Java string.equals(string) not behaving as expected - java

I am getting the occasional odd result from String.equals(String).
here is the code:
boolean equals(OutputHolder other){
boolean result=true;
if( ! this.speciesEng.equals(other.speciesEng))
result=false;
else if( ! this.date.equals(other.date))
result=false;
else if( ! this.gridRef.equals(other.gridRef))
result=false;
else if( ! this.recorder.equals(other.recorder))
result=false;
return result;
}
All pretty straight forward but on some objects .equals() returns false on what appear to be 2 identical strings.
This is a screenshot of the Expressions watchlist when the error occurs. As you can see this.speciesEng.equals(other.speciesEng) is returning false despite the fact that both strings appear the same.
The strings are initially from the same string resource but both have passed over an XMPP connection and back.
EDIT: To pass them over the XMPP connection, they have been concatenated with other strings to represent the whole OutputHolder. They are then separated on return using .substring(start,end). It occurred to me that it might make a difference if I made a new string from the substring but that didn't have any effect. Neither did trimming them.
I am at a loss as to how to proceed with debugging the problem. Any help or suggestions welcome.

There might be some whitespaces in there. Use String#trim method prior to calling equals.

Make sure there are no trailing spaces. So better use trim method on the strings before comparing them using equals method.

I think you should first trim both the strings and get rid of additional spaces.
That way you will be able to equate both the Strings properly.
Example Code:
String yourString = "Your String ";
//Trim the String and get rid of extra spaces before doing any comparisons.
yourString.trim();
//After trimming it, do the comparisons.
if(yourString.equalsIgnoreCase("other trimmed string"))
{
.....
}
I hope this helps.

After god knows how many hours copying and pasting from the debugger to a hex editor I have found the problem and a solution that works.
As suggested the problem was whitespaces but not in the way I or (I think) others suspected.
For some reason that I have failed to get to the bottom of, I am getting non-breaking whitespaces (0x00A0) in my strings instead of normal whitespaces (Ox0020). This appears to be happening more or less at random and I haven't found the section of code responsible yet.
The work around at the moment is to start my equals() method with:
speciesEng=speciesEng.replace((char)0x00a0,(char)0x0020);
other.speciesEng=other.speciesEng.replace((char)0x00a0,(char)0x0020);
speciesEng=speciesEng.trim();
other.speciesEng=other.speciesEng.trim();
Far from elegant but it works for the moment. I'll leave the question open for a couple of days in case anyone has more to add.
Thanks to all for the answers.

boolean equals(OutputHolder other){
boolean t1 = speciesEng.equals(other.speciesEng);
boolean t2 = date.equals(other.date);
boolean t3 = gridRef.equals(other.gridRef);
boolean t4 = recorder.equals(other.recorder);
return t1 && t2 && t3 && t4;
}

Related

Selenium Comparison

I am working on a Selenium test using WebDriver in Java. I have a compare that isn't comparing. The code looks like this:
if("20".equals(UserMaintenancePage.UserCount.getText()))
The value of the UserCount element is definitely 20 but it always fails the compare.
I tried slapping a .toString() on the end with the same result.
This one has me scratching my head.
Thanks
Use this
String val = UserMaintenancePage.UserCount.getText();
int intVal = Integer.parseInt(val);
if(intVal == 20) {
// to do your message
}
String str = Integer.toString("20");
if(str.equal(UserMaintenancePage.UserCount.getText()))
{}
I think the code might be failing due to "UserMaintenancePage.UserCount.getText()" is returning "20 " or " 20" instead of "20". So you can use .trim() function to clear blank spaces. I hope below mentioned code works for you:
if("20".equals(UserMaintenancePage.UserCount.getText().trim()))
{
// write your code..
}
Hope this helps :)
There were occasional extra characters getting into the webelement. Placing a .trim() on it everytime solved the problem.
Thanks for bearing with me on here.

Integer.toString() add "\u0000" characters, and if statement fails... [duplicate]

This question already has answers here:
How do I compare strings in Java?
(23 answers)
Closed 7 years ago.
OK, my first question in stackOverflow.
This is something that I left me completely baffled.
Java (I use android Studio), I write the following code:
Integer aNumber = 200;
String aNumberInString;
aNumberInString = Integer.toString(aNumber);
Boolean result;
if(aNumberInString == "200"){
result = true;
} else {
result = false;
}
Log.i("result:",result+"");
OK, logic and what I expect is that the condition is true... But NO! it fails.
I was really shocked by this behavior, then investigate a little more, and run the code in debug mode step by step.
when I get to the condition, I inspect the value of "aNumberInString" and to my surprise, this is what I find:
OK, so the first thing I think is: "Integer.toString ()" are doing something wrong.
Let's try another way: "String.valueOf ()"
Run in debug mode, and:
THE SAME! and fails, of course.
Obviously fails because it compares different characters, and in Internet I found a way to fix it,
string.replace ("\\ u0000", "");
but my question is not how to fix it, is:
Why is this happening?
Is there a correct way to prevent this from happening?
From already thank you very much to all,
Regards, Nicolas
You are doing a reference comparison. For comparing Strings, you need to call equals. By doing == with an Object, you are asking Java to make sure they are the same object, not if they have the same value.
Change:
if(aNumberInString == "200"){
To this:
if(aNumberInString.equals("200") {
Or better yet, to reduce the chance of a NullPointerExcpetion:
if("200".equals(aNumberInString))

Save Humanity Code in Hacker Rank

There is a problem under string domain in Hacker Rank, named as Save Humanity
with Link
https://www.hackerrank.com/contests/princetonolympics/challenges/save-humanity.
The are two strings given under the condition that if the two strings are equals its returns true and if there is a one-bit-error in the string then it returns true with the error indices.
Otherwise False for every other case.
My solution works fine for some test-cases,but for some test-cases the result is a timeout.
The question is how to decrease the Complexity.
For checking the one-bit-error I am using charAt function. Due to this the complexity rises.
Please help.
If I understand you correctly you have two strings that you want to compare, but you want to accept them even if the they differ in one character.
This can be done in one loop by just comparing the strings byte by byte.
char[] a = "abc".toCharArray();
char[] b = "abb".toCharArray();
boolean oneDiff = false;
for (int i = 0; i<){
if(a[i] != b[i]){
if(oneDiff)
return false;
oneDiff = true;
}
}
return true;
This has a time complexity of just O(n), which should be fast enough for most cases. If you need faster algorithms you can maybe research Edit Distance which is the name of this problem in the general case, but I don't think there are any faster algorithms.

if statement not working to filter empty names [duplicate]

This question already has answers here:
Closed 10 years ago.
Possible Duplicate:
If statement using == gives unexpected result
Hi I'm using this code to add elements to my ComboBox, and I do not want to add empty elements, here's the code:
public void elrendezesBetoltes(ArrayList<Elrendezes> ElrLista){
int i;
Elrendezes tmp;
model.removeAllElements();
model = new DefaultComboBoxModel(comboBoxItems);
for(i=0; i<ElrLista.size(); i++){
tmp = ElrLista.get(i);
if(tmp.getName()!="")comboBoxItems.add(tmp.getName()); //not working
addButton2(tmp.getSeatnum(),tmp.getCoord(),tmp.getFoglalt());
}
}
My problem is that the if statement is not working, it still adds empty names to my combobox. What am I doing wrong?
Always use equals method to compare Strings: -
if (tmp.getName()!="")
should be: -
if (!tmp.getName().equals(""))
or simply use this, if you want to check for empty string: -
if (!tmp.getName().isEmpty()) {
comboBoxItems.add(tmp.getName());
}
Use equals method to compare string. By using != operator, you are comparing the string instances, which is always going the be true as they(tmp.getName() and "") are not same string instances.
Change
tmp.getName()!=""
to
!"".equals(tmp.getName())
Putting "" as first string in comparison will take care of your null scenario as well i.e. it will not break if tmp.getName() is null.
Use equals():
if (!tmp.getName().equals(""))
Using == or != compares string references, not string contents. This is almost never what you want.
you have to compare Strings with "equals", then it will work
if(!tmp.getName().equals(""))comboBoxItems.add(tmp.getName())
you are comparing for identity (==, !=) but each String instance has its own identity, even when they are equal.
So you need to do !tmp.getName().equals("").
Generally it is considered best practice to start with the constant string first, because it will never be null: !"".equals(tmp.getName())
However, I would recommend to use apache commons lang StringUtils. It has a notEmpty() and notBlank() method that take care of null handling and also trimming.
PS: sometimes identity will work for Strings. but it should not be relied upon as it is caused by compiler or jvm optimization due to String immutability.
Use String#isEmpty()
if(!tmp.getName().isEmpty())
OR:
if(!tmp.getName().equals(""))
Always, check String equality with equals method. == operator only checks if two references point to the same String object.
Another alternative if not on Java 6 and isEmpty is unavailable is this:
if (tmp.getName.length()>0)
Checking for the length is supposed to be quicker than using .equals although tbh the potential gain is so small its not worth worrying too much about.

I asked a question about arrays before, but this one won't compile

I asked about this array a little while ago, and I can't see what the problem is. Too tired. What have I done wrong? Basically, I am taking a string array and trying to check to see if it contains numbers or an x (ISBN number validation). I want to take the number from a given input (bookNum), check the input, and feed any valid input into a new array (book). At the line
'bookNum.charAt[j]==book[i]'
I get the 'not a statement error'. What gives?
String[] book = new String [ISBN_NUM];
bookNum.replaceAll("-","");
if (bookNum.length()!=ISBN_NUM)
throw new ISBNException ("ISBN "+ bookNum + " must be 10 characters");
for (int i=0;i<bookNum.length();i++)
{
if (Character.isDigit(bookNum.charAt(i)))
bookNum.CharAt[j]==book[i];
j++;
if (book[9].isNotDigit()||
book[9]!="x" ||
book[9]!="X")
throw new ISBNException ("ISBN " + bookNum + " must contain all digits" +
"or 'X' in the last position");
== is java is used for equivalence comparison. If you want to assign it, use a single =.
The first issue here is that charAt is a function, and thus needs parenthesis even though you are accessing with an index like an array.
The other issue is that the line is a boolean expression, which just by itself does not mean anything. A lot of people are suggestion that you mean to make an assignment to that character, but just changing to a single equals causes other problems. The left side of an equals sign needs to be a variable, and the result of a function is not a variable.
Strings are immutable, so you can not simply change one of the characters in the string. Earlier in your code, you have a call to replaceAll(), that returns a new string with the alterations. As written, this altered string is being lost.
There are few odd problems here. For starters, did you mean for book to be an array of Strings, as opposed to just one string? You're trying (assuming CharAt was written properly and the assignment was proper) to assign a character to a string.
Second, instead of copying character by character, why not check the whole string, and copy the whole thing at the end if it is a proper ISBN? Depending on what you do with Exceptions (if you continue regardless), you could add a boolean as a flag that gets set if there is an error. At the end, if there is no error, then make book = to booknumber.replace(etc...)
bookNum.CharAt[j]==book[i];
Should be
bookNum.CharAt[j]=book[i];
You are using an equality boolean operator, not an assignment one.
Looks like you're using .charAt(i) wrong! Assuming that "bookNum" is a String, you should use:
bookNum.charAt(i)==book[i];
Instead. Note that this is a boolean expression, and not "=".
The line bookNum.CharAt[j]==book[i]; isn't a statement. It's a comparison. Perhaps you want bookNum.CharAt[j]=book[i]; (single = instead of ==).
Edit: That's not going to fix things, though, since you can't assign to bookNum.CharAt[j].

Categories