<commit_before>// Copyright 2013 <NAME>
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

package de.undercouch.citeproc.helper.tool;

import java.io.PrintStream;
import java.util.ArrayList;
import java.util.List;

import de.undercouch.citeproc.helper.tool.Option.ArgumentType;

/**
 * Parses command line options and prints usage information
 * @author <NAME>
 */
public class OptionParser {
	/**
	 * Print usage information
	 * @param <T> option identifier type
	 * @param command the command that has to be called in order
	 * to use the application
	 * @param description the application's description
	 * @param options the options to print out
	 * @param out destination stream
	 */
	public static <T> void usage(String command, String description,
			List<Option<T>> options, PrintStream out) {
		out.println("Usage: " + command);
		out.println(description);
		out.println();
		
		//calculate column widths
		int firstColumnWidth = 0;
		int secondColumnWidth = 0;
		for (Option<T> o : options) {
			//calculate width of first column (short name)
			if (o.getShortName() != null) {
				int fcw = o.getShortName().length() + 1;
				if (fcw > firstColumnWidth) {
					firstColumnWidth = fcw;
				}
			}
			
			//calculate width of second column (long name)
			int scw = o.getLongName().length() + 2;
			if (o.getArgumentType() != ArgumentType.NONE) {
				scw += o.getArgumentName().length() + 3;
			}
			if (scw > secondColumnWidth) {
				secondColumnWidth = scw;
			}
		}
		
		//output options
		for (Option<T> o : options) {
			out.print("  ");
			
			//output short name
			if (firstColumnWidth > 0) {
				int snl = 0;
				if (o.getShortName() != null) {
					out.print("-" + o.getShortName() + ",");
					snl = o.getShortName().length();
				} else {
					out.print("  ");
				}
				int pad = firstColumnWidth - snl - 1;
				while (pad > 0) {
					out.print(" ");
					--pad;
				}
			}
			
			//output long name
			int lnl = o.getLongName().length();
			out.print("--" + o.getLongName());
			if (o.getArgumentType() != ArgumentType.NONE) {
				out.print(" <" + o.getArgumentName() + ">");
				lnl += o.getArgumentName().length() + 3;
			}
			int pad = secondColumnWidth - lnl - 1;
			while (pad > 0) {
				out.print(" ");
				--pad;
			}
			
			//output description (wrap it if needed)
			out.print(" ");
			int w = firstColumnWidth + secondColumnWidth + 4;
			if (firstColumnWidth > 0) {
				w++;
			}
			String desc = o.getDescription();
			while (w + desc.length() > 75) {
				int sp = desc.lastIndexOf(' ', 74 - w);
				if (sp == -1) {
					break;
				}
				out.println(desc.substring(0, sp));
				for (int i = 0; i < w; ++i) {
					out.print(" ");
				}
				desc = desc.substring(sp + 1);
			}
			out.println(desc);
		}
	}
	
	/**
	 * Parses a command line and returns a list of parsed values
	 * @param <T> option identifier type
	 * @param args the command line
	 * @param options the options to parse
	 * @param def the default option identifier for parameters
	 * that are not options
	 * @return a list of parsed values
	 * @throws MissingArgumentException if an option misses a required argument
	 * @throws InvalidOptionException if one of the arguments is unknown
	 */
	public static <T> List<Value<T>> parse(String[] args, List<Option<T>> options,
			T def) throws MissingArgumentException, InvalidOptionException {
		List<Value<T>> result = new ArrayList<Value<T>>();
		for (int i = 0; i < args.length; ++i) {
			String a = args[i];
			
			boolean found = false;
			
			if (a.startsWith("--")) {
				//handle long name options
				String an = a.substring(2);
				for (Option<T> o : options) {
					if (o.getLongName().equals(an)) {
						i += parseValue(o, args, i, result);
						found = true;
						break;
					}
				}
			} else if (a.startsWith("-")) {
				//handle short name options
				String an = a.substring(1);
				for (Option<T> o : options) {
					if (o.getShortName().equals(an)) {
						i += parseValue(o, args, i, result);
						found = true;
						break;
					}
				}
			} else {
				//handle arguments that are not options
				result.add(new Value<T>(def, a));
				found = true;
			}
			
			if (!found) {
				throw new InvalidOptionException(args[i]);
			}
		}
		return result;
	}
	<commit_msg>Fixed NPE in command line tool<commit_after>// Copyright 2013 <NAME>
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

package de.undercouch.citeproc.helper.tool;

import java.io.PrintStream;
import java.util.ArrayList;
import java.util.List;

import de.undercouch.citeproc.helper.tool.Option.ArgumentType;

/**
 * Parses command line options and prints usage information
 * @author <NAME>
 */
public class OptionParser {
	/**
	 * Print usage information
	 * @param <T> option identifier type
	 * @param command the command that has to be called in order
	 * to use the application
	 * @param description the application's description
	 * @param options the options to print out
	 * @param out destination stream
	 */
	public static <T> void usage(String command, String description,
			List<Option<T>> options, PrintStream out) {
		out.println("Usage: " + command);
		out.println(description);
		out.println();
		
		//calculate column widths
		int firstColumnWidth = 0;
		int secondColumnWidth = 0;
		for (Option<T> o : options) {
			//calculate width of first column (short name)
			if (o.getShortName() != null) {
				int fcw = o.getShortName().length() + 1;
				if (fcw > firstColumnWidth) {
					firstColumnWidth = fcw;
				}
			}
			
			//calculate width of second column (long name)
			int scw = o.getLongName().length() + 2;
			if (o.getArgumentType() != ArgumentType.NONE) {
				scw += o.getArgumentName().length() + 3;
			}
			if (scw > secondColumnWidth) {
				secondColumnWidth = scw;
			}
		}
		
		//output options
		for (Option<T> o : options) {
			out.print("  ");
			
			//output short name
			if (firstColumnWidth > 0) {
				int snl = 0;
				if (o.getShortName() != null) {
					out.print("-" + o.getShortName() + ",");
					snl = o.getShortName().length();
				} else {
					out.print("  ");
				}
				int pad = firstColumnWidth - snl - 1;
				while (pad > 0) {
					out.print(" ");
					--pad;
				}
			}
			
			//output long name
			int lnl = o.getLongName().length();
			out.print("--" + o.getLongName());
			if (o.getArgumentType() != ArgumentType.NONE) {
				out.print(" <" + o.getArgumentName() + ">");
				lnl += o.getArgumentName().length() + 3;
			}
			int pad = secondColumnWidth - lnl - 1;
			while (pad > 0) {
				out.print(" ");
				--pad;
			}
			
			//output description (wrap it if needed)
			out.print(" ");
			int w = firstColumnWidth + secondColumnWidth + 4;
			if (firstColumnWidth > 0) {
				w++;
			}
			String desc = o.getDescription();
			while (w + desc.length() > 75) {
				int sp = desc.lastIndexOf(' ', 74 - w);
				if (sp == -1) {
					break;
				}
				out.println(desc.substring(0, sp));
				for (int i = 0; i < w; ++i) {
					out.print(" ");
				}
				desc = desc.substring(sp + 1);
			}
			out.println(desc);
		}
	}
	
	/**
	 * Parses a command line and returns a list of parsed values
	 * @param <T> option identifier type
	 * @param args the command line
	 * @param options the options to parse
	 * @param def the default option identifier for parameters
	 * that are not options
	 * @return a list of parsed values
	 * @throws MissingArgumentException if an option misses a required argument
	 * @throws InvalidOptionException if one of the arguments is unknown
	 */
	public static <T> List<Value<T>> parse(String[] args, List<Option<T>> options,
			T def) throws MissingArgumentException, InvalidOptionException {
		List<Value<T>> result = new ArrayList<Value<T>>();
		for (int i = 0; i < args.length; ++i) {
			String a = args[i];
			
			boolean found = false;
			
			if (a.startsWith("--")) {
				//handle long name options
				String an = a.substring(2);
				for (Option<T> o : options) {
					if (o.getLongName().equals(an)) {
						i += parseValue(o, args, i, result);
						found = true;
						break;
					}
				}
			} else if (a.startsWith("-")) {
				//handle short name options
				String an = a.substring(1);
				for (Option<T> o : options) {
					if (o.getShortName() != null && o.getShortName().equals(an)) {
						i += parseValue(o, args, i, result);
						found = true;
						break;
					}
				}
			} else {
				//handle arguments that are not options
				result.add(new Value<T>(def, a));
				found = true;
			}
			
			if (!found) {
				throw new InvalidOptionException(args[i]);
			}
		}
		return result;
	}
	
{'fraction_non_alphanumeric': 0.13716024766502255, 'fraction_numerical': 0.006926225207262042, 'mean_word_length': 2.7182988685134606, 'pattern_counts': {'":': 0, '<': 51, '<?xml version=': 0, '>': 61, 'https://': 0, 'lorem ipsum': 0, 'www.': 2, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '5012377', 'n_tokens_mistral': 3684, 'n_tokens_neox': 2966, 'n_words': 967}