I'm trying to create a method, that deletes empty lines at the end of a string:
public static String deleteBlankLinesAtEnd(String input)
{
input = trimToEmptyString(input);
return input.replaceFirst("\\n{2,}\\z", "");
}
However, it seems to also delete empty lines in the beginning of the input.
I got a little unit test:
#Test
public void testDeleteBlankLinesAtEnd()
{
assertEquals("hej", TextUtils.deleteBlankLinesAtEnd("hej\n\n"));
assertEquals("hej\nhej", TextUtils.deleteBlankLinesAtEnd("hej\nhej\n\n"));
assertEquals("hej\n\nhej", TextUtils.deleteBlankLinesAtEnd("hej\n\nhej\n\n"));
assertEquals("\n\nhej\n\nhej", TextUtils.deleteBlankLinesAtEnd("\n\nhej\n\nhej\n\n"));
}
The 3 first runs fine, the last one fails.
Update: Of course, the trimToEmptyString() was my problem, since it also trims the beginning..
public static String trimToEmptyString(String input)
{
if (input == null)
{
return "";
}
return input.trim();
}
So everything with the regex, was working fine.
The regex looks OK; I suspect there's a problem with trimToEmptyString().
You could do something like so:
public static String deleteBlankLinesAtEnd(String input)
{
input = trimToEmptyString(input);
return input.replaceFirst("\\n{2,}\\z$", "");
}
The $ should instruct the regex to match anything just before the end of the string. In this case, it should match any new lines which are just prior to the end of the string.
How about to replace all blank lines including lines full of spaces.
input.replaceFirst("\\n\\s+$", "\n")
Related
Hi guys I'm writing a method which counts words in a file, but apparently there is a mistake somewhere in the code and the method does not work. Here's my code:
public class Main2 {
public static void main(String[] args) {
count("/home/bruno/Desktop/WAR_JEE_S_09_Podstawy/MojPlik");
}
static int count(String fileName){
Path path = Paths.get(fileName);
int ilosc = 0;
String wyjscie = "";
try {
for (String charakter : Files.readAllLines(path)){
wyjscie += charakter;
}
StringTokenizer token = new StringTokenizer(wyjscie," \n");
} catch (IOException e) {
e.printStackTrace();
}
return ilosc;
}
}
The file path is correct, here is the file content
test test
test
test
after i call the method in main it displays nothing. Where is the mistake ?
Your code would count lines in a file ... well, if you followed up on that thought.
Right ow your code is simply reading lines, putting them into one large string, to then do nothing about the result of that operation. You have a single int counter ... who is init'ed to 0, and then just returned without ever being used/increased! And unless I am mistaken, readAllLines() will automatically remove the newline char in the end, so overall, your code is nothing but useless.
To count words you have to take each line and (for example) split that one-line-string for spaces. That gives you a number. Then add up these numbers.
Long story short: the real answer here is that you should step back. Don't just write code, assuming that this will magically solve the problem. Instead: first think up a strategy (algorithm) that solves the problem. Write down the algorithm ideas using a pen and paper. Then "manually" run the algorithm on some sample data. Then, in the end, turn the algorithm into code.
Also, beside that you does not output anything, there is a slight error behind you logic. I have made a few changes here and there to get your code working.
s.trim() removes any leading and trainling whitespace, and trimmed.split("\\s+") splits the string at any whitespace character, including spaces.
static int count(String fileName) throws IOException {
Path path = Paths.get(fileName);
int count = 0;
List<String> lines = Files.readAllLines(path);
for (String s : lines) {
String trimmed = s.trim();
count += trimmed.isEmpty() ? 0 : trimmed.split("\\s+").length;
}
return count;
}
Here is the code using functional-style programming in Java 8. This is also a common example of using Stream's flatMap - may be used for counting or printing words from a file.
long n = Files.lines(Paths.get("test.txt"))
.flatMap(s -> Stream.of(s.split("\\s+")))
.count();
System.out.println("No. of words: " + n);
Note the Files.lines(Path) returns a Stream<String> which has the lines from the input file. This method is similar to readAllLines, but returns a stream instead of a List.
I'm writing these algorithms for a style-correcting program which makes adjustments to a java source file, that can compile without error. It is currently set to read the file line-by-line.
Right now, I'm having trouble writing 2 methods/algorithms which
Determine if the current line (string) has comments, and
finds where the comment starts
I currently have:
public static int FindComment (String TextLine) {
int EndOfCode = TextLine.lastIndexOf("; ");
return TextLine.indexOf("//", EndOfCode);
}
public static boolean HasComment (String TextLine) {
if (TextLine.contains("//"))
{
return true;
}
else
{
return false;
}
}
I know this is incorrect because I can have code, and comments, which contain " ; // ; //" as well as comments. I tried other conditional statements without success.
Hello you don't explain what problem do you have but I think you should escape with backslash characters when working with indexOf function.
I am making a method that prints lines in a file which contain a certain word. If the parameter is an empty String, it is supposed to print the entire file.
I've gotten the first part to work. Everything in the "else" statement works great; it scans each line and prints the lines that contain the word in the parameter.
BUT I can't get it to print the whole file when an empty String ("") is entered as the parameter "word". I'm not sure why this is.
public void printLinesWhichContain(String word) {
while (this.reader.hasNextLine()) {
String line = this.reader.nextLine();
if (word.isEmpty()) {
System.out.println(line);
} else {
Scanner lineReader = new Scanner(line);
while (lineReader.hasNext()) {
if (lineReader.next().equals(word)) {
System.out.println(line);
}
}
}
}
}
Once you have the line in String format, you can use the indexOf method to get the index of the word.
I wouldn't create a Scanner for each and every line.
I mean you might want to change the else part as follows.
int indexOfWord = line.indexOf(word);
if (indexOfWord >= 0)
{
System.out.println(line);
}
I'm reading in a text file formated like
word
definiton
word
definition
definition
word
definition
So I need to keep try of whether I'm in a definition or not based on when I reach those emtpy lines. Thing is, BufferedReader discards \n characters, and somehow comparing that empty line to String "" is not registering like I thought it would. How can I go about doing this.
Make sure you use: "".equals(myString) (which is null-safe) not myString == "".
After 1.6, you can use myString.isEmpty() (not null-safe)
You can use myString.trim() to get rid of extra whitespace before the above check
Here's some code:
public void readFile(BufferedReader br) {
boolean inDefinition = false;
while(br.ready()) {
String next = br.readLine().trim();
if(next.isEmpty()) {
inDefinition = false;
continue;
}
if(!inDefinition) {
handleWord(next);
inDefinition = true;
} else {
handleDefinition(next);
}
}
}
The BufferedReader.readLine() returns an empty string if the line is empty.
The javadoc says:
Returns: A String containing the contents of the line, not including any line-termination characters, or null if the end of the stream has been reached.
If you don't appear to be seeing an empty String, either the line is not empty, or you are not testing for an empty String correctly.
line = reader.readLine();
if ("".equals(line)) {
//this is and empty line...
}
I do not know how did you try to check that string is empty, so I cannot explain why it did not work for you. Did you probably use == for comparison? In this case it did not work because == compares references, not the object content.
This code snippets skips the empty line and only prints the ones with content.
String line = null;
while ((line = br.readLine()) != null) {
if (line.trim().equals("")) {
// empty line
} else {
System.out.println(line);
}
}
Lines only containing whitespace characters are also skipped.
try (BufferedReader originReader = getReader("now")) {
if (StringUtils.isEmpty(originReader.readLine())) {
System.out.printline("Buffer is empty");
}
As an exercise, the code block below intends to recursively go through a string and remove all the of the "x" characters. It does that, but I would like to keep track of the newStr without passing it as a parameter in the method. Is there anyway to move it into the method body?
Thanks!
public static String deathToX(String str, String newStr) {
//look for x char
if(str.substring(0, 1).equals("x")) {
//do nothing
} else {
//add non-x char to newStr
newStr += str.charAt(0);
}
if(str.length() == 1) {
return newStr;
}
return deathToX(str.substring(1), newStr);
}
public static void main(String[] args) {
System.out.println("Return: " + deathToX("xnoxmore", ""));
}
Well, you could change the code to:
public static String deathToX(String str)
{
// Termination case
if (str.length() == 0)
{
return str;
}
// Work out whether or not we want the first character
String prefix = str.startsWith("x") ? "" : str.substring(0, 1);
// Let the recursive call handle the rest of the string, and return
// the prefix (empty string or the first character) followed by the
// x-stripped remainder.
return prefix + deathToX(str.substring(1));
}
Is that the sort of thing you were thinking of?
Of course, this is a horribly inefficient way of doing string manipulation, but I assume you're more interested in the recursive nature of things.
I would like to keep track of the newStr without passing it as a parameter in the method.
Why? Passing the intermediary result into the function is often required in functional-style recursive programming. What I do is make a function that handles the bulk of the work and accepts the accumulator, and make a wrapper function that calls the previous one with the required starter value:
private static String deathToX0(String str, String newStr) {
// the original implementation
}
public static String deathToX(String str) {
return deathToX(str, "");
}
As an aside, you might not want to use a String for the intermediate result because of the copying involved. A StringBuilder would be faster.
The short answer is yes... with recursion typically on the way down the tree you work out the bit at each level in this case blank or the current character. So the return statement should call itself recursively then at the bottom of the tree the answer you wanted is reconstructed by adding together the sections at each level.
public static String deathToX(String str){
if (!str.isEmpty()){
return (str.substring(0, 1).equals("x") ? "" : str.substring(0, 1)) + deathToX(str.substring(1));
}else{
return "";
}
}
public static void main(String[] args){
System.out.println("Return: " + deathToX("xnoxmore"));
}
In the sample above I used the shorthand if format to put it all on one line but you could expand it out. You should be able to see that the recursive function recurses on the return statement and I put in a special case for the last level. If you were to split it and put this levels answer in a local variable e.g. tmp then you would use:
return tmp + deathToX(str.substring(1));
Remember recursion means that the current execution is only paused until the lower ones finish so you can happily store info to recover on your way back up. Hope this helps :)
public class solution {
// Return the changed string
public static String removeX(String input){
if(input.equals("") || input.equals("x"))
return "";
String returnStr="";
removeX(input.substring(1));
for(int i=0;i<input.length();i++)
{
if(input.charAt(i)=='x')
continue;
else
returnStr+=input.charAt(i);
}
return returnStr;
}
}
This is my approach. This code goes to the end of the string, if it gets X as last string, it returns ""(nothing), then it checks the whole substring for "x", if its present in the string, it will continue, else it will append rest character to that string and it goes on.
Finally returns the updated string.!
Hope this helps..!! well, this is my first contribution here :)