/*
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF licenses this file
 * to you 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 org.apache.sysds.runtime.util;

import java.io.Serializable;
import java.util.NoSuchElementException;

/**
 * This string tokenizer is essentially a simplified StringTokenizer. 
 * In addition to the default functionality it allows to reset the tokenizer and it makes
 * the simplifying assumptions of (1) no returns delimiter, and (2) single character delimiter.
 * 
 */
public class FastStringTokenizer implements Serializable
{
	private static final long serialVersionUID = 4051436015710778611L;
	private String _string = null;
	private char   _del    = 0;
	private int    _pos    = -1;

	/**
	 * Constructs a new StringTokenizer for string using the specified
	 * delimiter
	 * 
	 * @param delimiter
	 *            the delimiter to use
	 */
	public FastStringTokenizer(char delimiter) {
		_del = delimiter;
		reset( null );
	}

	public void reset( String string ) {
		_string = string;
		_pos = 0;
	}
	
	/**
	 * Returns the next token in the string as a String.
	 * 
	 * @return next token in the string as a String
	 */
	public String nextToken() {
		int len = _string.length();
		int start = _pos;
		
		//find start (skip over leading delimiters)
		while(start < len && _del == _string.charAt(start) )
			start++;
		
		//find end (next delimiter) and return
		if(start < len) {
			_pos = _string.indexOf(_del, start);
			if( start < _pos && _pos < len )
				return _string.substring(start, _pos);
			else 
				return _string.substring(start);
		}
		//no next token
		throw new NoSuchElementException();
	}

	public int nextInt() {
		return Integer.parseInt( nextToken() );
	}

	public long nextLong() {
		return Long.parseLong( nextToken() );
	}

	public double nextDouble() {
		return UtilFunctions.parseToDouble(nextToken());
	}
}
