I have a text file as follows:
Title
XYZ
Id name
1 abc
2 pqr
3 xyz
I need to read the content starting with the integer value and I used the regular expression as in the following code.
public static void main(String[] args) throws FileNotFoundException {
FileInputStream file= new FileInputStream("C:\\Users\\ap\\Downloads\\sample1.txt");
Scanner scanner = new Scanner(file);
while (scanner.hasNextLine()) {
String line = scanner.nextLine();
if (line.startsWith("[0-9]")) {
System.out.println("Line: "+line);
}
}
}
The above code can't detect the lines starting with integers. However, it works fine if single integer values are passed to startsWith() function.
Please suggest, where I went wrong.
String#startsWith(String) method doesn't take regex. It takes a string literal.
To check the first character is digit or not, you can get the character at index 0 using String#charAt(int index) method. And then test that character is digit or not using Character#isDigit(char) method:
if (Character.isDigit(line.charAt(0)) {
System.out.println(line);
}
For regex you can use the "matches" method, like this:
line.matches("^[0-9].*")
Related
for the below input im expecting all the strings delimited with "|" to be available in an array. but only first string is available and the next string is partially available.the rest is not at all available. please help me in understanding it. i explored all the help docs and previous stackoverflow stuff but not able to solve it. i tried with split(String regex,int limit)as well but no use. I dont want to replace the whitespace as i need to retain that.
input "1|New York|1345|134|45634"
Expected output is: 1,New York,1345,134,45634
Actual output is:1,New
public class test1 {
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
String strinp=scanner.next();
//System.out.println(strinp.replaceAll(" ", ""));
String[] strArr=strinp.split("\\|");
//System.out.println(Arrays.deepToString(strArr));
for (String s:strArr) {
System.out.println(s);
}
}
}
scanner.next() splits on spaces itself. So your first scanner.next() call reads 1|New which you then split.
Use scanner.nextLine() to read the whole line, it will be split successfully.
Change:
String strinp = scanner.next();
To:
String strinp = scanner.nextLine();
Or you can declare scanner as:
Scanner scanner = new Scanner(System.in).useDelimiter("\\n");
This question already has answers here:
Scanner doesn't read whole sentence - difference between next() and nextLine() of scanner class
(24 answers)
Closed 5 years ago.
My initial code that does not produce the desired result:
import java.util.Scanner;
class Strings {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
System.out.println("Enter your word: ");
String word1 = sc.next();
System.out.println(word1.length());
sc.close();
}
}
Output:
tk#localhost:~$ java Strings
Enter your word:
avada kedavra
5
Which is not the length of my string.
But when I try this(without the user input) :
class Strings {
public static void main(String[] args) {
String str = new String("avada kedavra");
System.out.println(str.length());
}
}
Output :
tk#localhost:~$ java Strings
13
It works!
So , why doesn't it work when I take input from the user? What am I missing?
By default, sc.next() finds and returns the next complete token. By default, a token is a word, something separated with spaces or newline (\p{javaWhitespace}+).
So in your first example, word1 = "avada", with length 5.
Use sc.nextLine() to get the complete line.
In short: RTFM
A bit longer for the click-lazy: Scanner returns the "next token" when calling next Tokens are calculated by taking a pattern, which is "all whitespaces" by default. So your call of next returns the next word and not the complete line as you intended.
Set a fitting pattern when instantiating Scanner or call nextLine instead.
I'm trying to do some homework for my computer science class and I can't seem to figure this one out. The question is:
Write a program that reads a line of text and then displays the line, but with the first occurrence of hate changed to love.
This sounded like a basic problem, so I went ahead and wrote this up:
import java.util.Scanner;
public class question {
public static void main(String[] args)
{
Scanner keyboard = new Scanner(System.in);
System.out.println("Enter a line of text:");
String text = keyboard.next();
System.out.println("I have rephrased that line to read:");
System.out.println(text.replaceFirst("hate", "love"));
}
}
I expect a string input of "I hate you" to read "I love you", but all it outputs is "I". When it detects the first occurrence of the word I'm trying to replace, it removes the rest of the string, unless it's the first word of the string. For instance, if I just input "hate", it will change it to "love". I've looked at many sites and documentations, and I believe I'm following the correct steps. If anyone could explain what I'm doing wrong here so that it does display the full string with the replaced word, that would be fantastic.
Thank you!
Your mistake was on the keyboard.next() call. This reads the first (space-separated) word. You want to use keyboard.nextLine() instead, as that reads a whole line (which is what your input is in this case).
Revised, your code looks like this:
import java.util.Scanner;
public class question {
public static void main(String[] args)
{
Scanner keyboard = new Scanner(System.in);
System.out.println("Enter a line of text:");
String text = keyboard.nextLine();
System.out.println("I have rephrased that line to read:");
System.out.println(text.replaceFirst("hate", "love"));
}
}
Try getting the whole line like this, instead of just the first token:
String text = keyboard.nextLine();
keyboard.next() only reads the next token.
Use keyboard.nextLine() to read the entire line.
In your current code, if you print the contents of text before the replace you will see that only I has been taken as input.
As an alternate answer, build a while loop and look for the word in question:
import java.util.Scanner;
public class question {
public static void main(String[] args)
{
// Start with the word we want to replace
String findStr = "hate";
// and the word we will replace it with
String replaceStr = "love";
// Need a place to put the response
StringBuilder response = new StringBuilder();
Scanner keyboard = new Scanner(System.in);
System.out.println("Enter a line of text:");
System.out.println("<Remember to end the stream with Ctrl-Z>");
String text = null;
while(keyboard.hasNext())
{
// Make sure we have a space between characters
if(text != null)
{
response.append(' ');
}
text = keyboard.next();
if(findStr.compareToIgnoreCase(text)==0)
{
// Found the word so replace it
response.append(replaceStr);
}
else
{
// Otherwise just return what was entered.
response.append(text);
}
}
System.out.println("I have rephrased that line to read:");
System.out.println(response.toString());
}
}
Takes advantage of the Scanner returning one word at a time. The matching will fail if the word is followed by a punctuation mark though. Anyway, this is the answer that popped into my head when I read the question.
I'm trying to print a string in reverse. i.e.
hello world
should come out as:
dlrow olleh
But the outcome only shows the reverse of the first word. i.e.
olleh
Any thoughts?
import java.util.Scanner;
public class test {
public static void main(String[] args) {
// TODO Auto-generated method stub
Scanner input = new Scanner(System.in);
System.out.println("Input a string:");
String s;
s = input.next();
String original, reverse = "";
original = s;
int length = original.length();
for ( int i = length - 1 ; i >= 0 ; i-- )
reverse = reverse + original.charAt(i);
System.out.println("Reverse of entered string is: "+reverse);
input.close();
}
}
Using input.next() only stores the next word in the variable (only "hello"). Try this:
System.out.println("Input a string:");
String s;
s = input.nextLine();
System.out.println("entered: " + s);
The line
s=input.next()
will only take one word.
So to get the whole line 'hello world', you've to use the nextLine() function.
s = input.nextLine();
Your scanner object returns only the next complete token through the input.next() method. A token is considered complete when there is a whitespace character. Use the nextLine() method of the scanner to get the complete input if you are using multiple words.
new StringBuilder("hello world").reverse().toString();
Maybe much more simpler.
use s.nextline() instead of s.next() as s.next() read only first token string
Scanner sc= new Scanner(System.in);
String s = sc.nextLine();
System.out.println(new StringBuilder(s).reverse().toString());
From Scanner javadoc:
public String next()
Finds and returns the next complete token from this scanner. A
complete token is preceded and followed by input that matches the
delimiter pattern. This method may block while waiting for input to
scan, even if a previous invocation of hasNext() returned true.
What happens is that the token delimiter may not be what you're expecting (newline, for instance).
If you wish your program to read the entire line input by the user, you might want to use Scanner.nextLine(), which will read the entire line input by the user, or maybe Scanner.next(String delimiter), which will allow you to enter the desired token delimiter.
Change s = input.next() to s = input.nextLine()
I can't really write some source code but maybe try using two different inputs. After that add each string to it's own variable. After that, reverse them both and add them together as an output.
In java i would like to read a file line by line and print the line to the output.
I want to solve this with regular expressions.
while (...)
{
private static java.util.regex.Pattern line = java.util.regex.Pattern.compile(".*\\n");
System.out.print(scanner.next(line));
}
The regex in the code is not correct, as i get InputMismatchException.
I am working on this regex for 2 hours. Please help with it.
With regex powertoy i see that ".*\n" is correct. But my program runs incorrectly.
The whole source is:
/**
* Extracts the points in the standard input in off file format to the standard output in ascii points format.
*/
import java.util.regex.Pattern;
import java.util.Scanner;
class off_to_ascii_points
{
private static Scanner scanner = new Scanner(System.in);
private static Pattern fat_word_pattern = Pattern.compile("\\s*\\S*\\s*");
private static Pattern line = Pattern.compile(".*\\n", Pattern.MULTILINE);
public static void main(String[] args)
{
try
{
scanner.useLocale(java.util.Locale.US);
/* skip to the number of points */
scanner.skip(fat_word_pattern);
int n_points = scanner.nextInt();
/* skip the rest of the 2. line */
scanner.skip(fat_word_pattern); scanner.skip(fat_word_pattern);
for (int i = 0; i < n_points; ++i)
{
System.out.print(scanner.next(line));
/*
Here my mistake is.
next() reads only until the delimiter,
which is by default any white-space-sequence.
That is next() does not read till the end of the line
what i wanted.
Changing "next(line)" to "nextLine()" solves the problem.
Also, setting the delimiter to line_separator
right before the loop solves the problem too.
*/
}
}
catch(java.lang.Exception e)
{
System.err.println("exception");
e.printStackTrace();
}
}
}
The beginning of an example input is:
OFF
4999996 10000000 0
-28.6663 -11.3788 -58.8252
-28.5917 -11.329 -58.8287
-28.5103 -11.4786 -58.8651
-28.8888 -11.7784 -58.9071
-29.6105 -11.2297 -58.6101
-29.1189 -11.429 -58.7828
-29.4967 -11.7289 -58.787
-29.1581 -11.8285 -58.8766
-30.0735 -11.6798 -58.5941
-29.9395 -11.2302 -58.4986
-29.7318 -11.5794 -58.6753
-29.0862 -11.1293 -58.7048
-30.2359 -11.6801 -58.5331
-30.2021 -11.3805 -58.4527
-30.3594 -11.3808 -58.3798
I first skip to the number 4999996 which is the number of lines containing point coordinates. These lines are that i am trying to write to the output.
I suggest using
private static Pattern line = Pattern.compile(".*");
scanner.useDelimiter("[\\r\\n]+"); // Insert right before the for-loop
System.out.println(scanner.next(line)); //Replace print with println
Why your code doesn't work as expected:
This has to do with the Scanner class you use and how that class works.
The javadoc states:
A Scanner breaks its input into tokens
using a delimiter pattern, which by
default matches whitespace.
That means when you call one of the Scanner's.next* methods the scanner reads the specified input until the next delimiter is encountered.
So your first call to scanner.next(line) starts reading the following line
-28.6663 -11.3788 -58.8252
And stops at the space after -28.6663. Then it checks if the token (-28.6663) matches your provided pattern (.*\n) which obviously doesn't match (-28.6663). That's why.
If you only want to print the file to standard out, why do you want to use regexps? If you know that you always want to skip the first two lines, there are simpler ways to accomplish it.
import java.util.Scanner;
import java.io.File;
public class TestClass {
public static void main(String[] args) throws Exception {
Scanner in=new Scanner(new File("test.txt"));
in.useDelimiter("\n"); // Or whatever line delimiter is appropriate
in.next(); in.next(); // Skip first two lines
while(in.hasNext())
System.out.println(in.next());
}
}
You have to switch the Pattern into multiline mode.
line = Pattern.compile("^.*$", Pattern.MULTILINE);
System.out.println(scanner.next(line));
By default the scanner uses the white space as its delimiter. You must change the delimiter to the new line before you read the line after the first skips. The code you need to change is to insert the following line before the for loop:
scanner.useDelimiter(Pattern.compile(System.getProperty("line.separator")));
and update the Pattern variable line as following:
private static Pattern line = Pattern.compile(".*", Pattern.MULTILINE);
Thank everybody for the help.
Now i understand my mistake:
The API documentation states, that every nextT() method of the Scanner class first skips the delimiter pattern, then it tries to read a T value. However it forgets to say that each next...() method reads only till the first occurrence of the delimiter!