Here's where I wish Java's String class had a replaceLast method, bu it doesn't and I'm getting the wrong results with my code.
I'm writing a program that searches a data structure for any items that match a string prefix. However, since I'm using an Iterator, the last item returned by the iter.next() call doesn't match the pattern, so I want to change the search string so that the last character of the query is increased by one letter. My testing code is returning [C#b82368 with this code and An as titleSearch:
public String changeLastCharacter(String titleSearch) {
char[] temp= titleSearch.toCharArray();
char lastLetter= temp[temp.length-1];
lastLetter++;
temp[temp.length-1]= lastLetter;
String newTitleSearch= temp.toString();
return newTitleSearch;
}
First, what is the cause of the output from this code?
Second, is there a better way to execute my solution?
You want:
newTitleSearch = new String(temp);
The toString method is not overridden for arrays; it's the usual Object.toString, intended for debugging. The above actually creates a string of the characters. An alternative is:
int len = titleSearch.length();
String allButLast = titleSearch.substring(0, len - 1);
newTitleSearch = allButLast + new Character(titleSearch.charAt(len - 1) + 1);
Whenever you see unexpected output like ....#<hex-digits>, the chances are that you are accidentally using toString() on some object whose class inherits the default implementation from Object.
The default toString() method returns a String whose value consists of the type name for the object combined with the object's "identity hash code" as hex digits. In your case the [C part is the type name for a char[] object. The '[' means "array of" and the 'C' means the char primitive type.
The rules for forming the type names used in the default toString() method are fully documented in the javadocs for java.lang.Class.getName().
Your problem is temp.toString(). Try String newTitleSearch = new String(temp); instead.
I figured this out by System.out.println(temp[0]+","+temp[1]); after temp[1] add been assigned to the incremented value. You could do this even easier by using your IDE's debugger.
Since the array was being assigned properly, the problem had to be in the toString().
Related
As you may know Object has some function,
For example we have toString() from oracle Documentacion we can know by default it's return HexValue of hashCode()
https://docs.oracle.com/javase/7/docs/api/java/lang/Object.html#toString()
We also can use hashCode() for checking of equality object (of course implementation depends on you)
So I made implementation for my Class Projekt :
public class Projekt {
int i;
public Projekt(int i) {
this.i=i;
// TODO Auto-generated constructor stub
}
#Override
public int hashCode() {
final int prime = 31;
int result = 1;
result = prime * result + i;
return result;
}
}
Test Code:
Projekt projekt = new Projekt(1);
System.out.println(projekt.toString());
System.out.println(projekt.toString() == projekt.toString());
Output:
Projekt#20
false
Also i try to inside value from projekt.toString() in StringPool by writing:
String string = projekt.toString();
String stringABC = projekt.toString();
System.out.println(string == stringABC);
According to PoolString i should have the same reference but outPrint is false.
So this method return different reference value but i can't understand why?
From your comment:
I copied this from diffrent comenatry: But to save memory we're using StringPool. If we have the same value, refereance is also the same it's working just for creating String not by constructor. If i had String s = new String("a"); String s2 = new String("a"); I used 2 space in memory, but when i use String s = "a"; String s2 = "a" I use 1 space in memory. So that's mean toString() return "new String()"?
Your source should have said:
...it's working just for creating String using string literals.
That way it might have been clearer, because there are many ways to create new String objects without directly calling the constructor. String literals are those things surrounded by " (including the quotes), such as "a" or "b" or "Welcome to Stack Overflow".
Only string literals1 are pooled automatically. You can manually put a string into the pool by calling intern().
When you concatenate two strings (e.g. stringA + stringB), a new string is generally created, as described here.
Now let's look at what Object.toString does:
The toString method for class Object returns a string consisting of
the name of the class of which the object is an instance, the at-sign
character `#', and the unsigned hexadecimal representation of the hash
code of the object. In other words, this method returns a string equal
to the value of:
getClass().getName() + '#' + Integer.toHexString(hashCode())
Note that strings are being concatenated here, so a new string object is being created here, hence the output.
And to answer the question of:
So that's mean toString() return "new String()"?
Yes, but not directly. The compiler will turn the + operators in Object.toString into some code using StringBuilder (or rather, "the compiler has turned..." since the Object class has already been compiled). At the end, it will call StringBuilder.toString, and that will create a new String object.
1Constant expressions of strings, to be more accurate.
This is because "toString()" method returns a string. So everytime you call toString() it returns a new reference because Strings are immutable (even if they're the same text)
String class is just a pointer to string (char) data somewhere in the memory. It is a class, it is not a primitive type like boolean, byte, char, short, int, long, float and double.
So, comparing two strings you compare pointers.
You generate two strings in:
String string = projekt.toString();
String stringABC = projekt.toString();
So you have 2 different pointers now. They have the same text inside, but they are in different places in memory.
But you can use equals() method of object:
System.out.println(string.equals(stringABC));
I wanted to create a char array of the alphabet. I looked at this post:
Better way to generate array of all letters in the alphabet
which said this:
char[] alphabet = "abcdefghijklmnopqrstuvwxyz".toCharArray();
So in my code I have:
public class Alphabet {
private char[] letters = "ABCDEFGHIJKLMNOPQRSTUVWXYZ".toCharArray();
public String availableLetters(){
return letters.toString();
}
}
When I call the function availableLetters() from main() and printit to the console, it outputs this garbage:
[C#15db9742
What am I doing wrong?
The array is correct, the problem is that you are not printing it correctly.
If you print your array one character at a time, you would get a correct result:
for (char c : letters) {
System.out.print("'" + c + "' ");
}
demo
Unfortunately, Java standard class library does not provide a meaningful override of toString() for arrays, causing a lot of trouble for programmers who are new to the language.
If you want to print it in array form, then use:
System.out.println(Arrays.toString(letters));
BTW: The [C#15db9742 is not really garbage. It's what gets printed out when a class does not override the toString() method.
From Object.toString():
Returns a string representation of the object. In general, the
toString method returns a string that "textually represents" this
object. The result should be a concise but informative representation
that is easy for a person to read. It is recommended that all
subclasses override this method. The toString method for class Object
returns a string consisting of the name of the class of which the
object is an instance, the at-sign character `#', and the unsigned
hexadecimal representation of the hash code of the object. In other
words, this method returns a string equal to the value of:
getClass().getName() + '#' + Integer.toHexString(hashCode())
You can pass the char array to the String constructor or the static method String.valueOf() and return that instead.
I know how to take integer value to string like
String s = st.getText().toString(0;
but my question is how we will take for a character... suppose the value ofa textView txt1 = 'A' so how we will take the value to a string str1..
String str1 = txt1.getText().toString();
is it correct....?
TextView.getText() return java.lang.CharSequence , and ideally you should be able to apply toString() to get the String value. But, however,
from CharSequence java doc
This interface does not refine the general contracts of the equals and
hashCode methods. The result of comparing two objects that implement
CharSequence is therefore, in general, undefined. Each object may be
implemented by a different class, and there is no guarantee that each
class will be capable of testing its instances for equality with those
of the other. It is therefore inappropriate to use arbitrary
CharSequence instances as elements in a set or as keys in a map.
CharSequence is an interface( though toString() appears as declared), it should work provided the CharSequence implementer did their job properly. To avoid any suprises, you can try a different approch
final StringBuilder sb = new StringBuilder(charSequence.length());
sb.append(charSequence);
return sb.toString();
String str1 = txt1.getText().toString();
Yes. It's the right answer to get the string value from string .
If getText() already returns a String, your job is already done for you. It's a string to begin with.
If you absolutely must create a String from a single char value, you can do so with the constructor that takes a char[] as an argument: new String(new char[] {value}).
If, as Satheesh stated above, it returns a CharSequence, there is also a String constructor that takes that as a parameter. Thus, it may be best to declare a new String(txt1.getText()) rather than relying on the implementation of the returned CharSequence's toString() method.
I'm new to java language I confused about different between these 2 methods calls (I don't know exactly it is method call or not)
but if i need to call method to calculate something I call this
salary obj=new salary();
obj.bonus(45000);
but when we call String length method we call this as
String name="Java lovely";
name.length();
What are the different of these 2 methods .Please help me to overcome this problem.
Thank you
String name="Java lovely";
You might confused with the string literal.
String is special in java
You will clear if I wrote
String s = new String("Java Lovely");
s.lenght();
String is a class. String class represents character strings. All string literals in Java programs, such as "abc", are implemented as instances of this class.
Strings are constant; their values cannot be changed after they are created. String buffers support mutable strings. Because String objects are immutable they can be shared. For example:
String str = "Java lovely";
is equivalent to:
char data[] = {'J', 'a', 'v', 'a', ' ', 'l','o', 'v', 'e','l', 'y'};
String str = new String(data);
length is a method of String Class.
in upper part that is
salary obj=new salary();
obj.bonus(45000);
in this salary is a class and you created object of this 'obj' and bonus is a method that you defined in salary class and you are calling that method
and other is
String name="Java lovely";
name.length();
is here same
String name=new String("Java lovely");
and you are calling length method on String object 'name'.
both are same but one difference is String is constant(immutable) mean once you created it, you can't change it but your salary class is not constant,you can change it.
To understand java better u can read this book. Head first Java
It is exactly same. Both obj and name are instance of their class. BUt String is exceptional class in java.. It can be create like above without new keyword.
it's the same, as String is a ready included java class.
you can make :
String name = new String("dsdsd");
it seems like
String name = new String();
name = "dsdsd";
name.length();
What do you men by difference?
That the first call has something between the () ? And name.length not? That is because the method bonus is an method with parameters. It expects an value, at this case an integer or int to do something with this. but Name.length doesnt mean any values, it just returns the saved length of the string.
Or where else you see a difference?
obj.bonus(number); and
name.length ();
is actually the same...
Sry if this wasnt your question.
Edit: or do you mean the constructor? This is because string is special in java, actually new String("lalala"); is right.
salary obj=new salary(); // You are initializing salary class
obj.bonus(45000); // Your salary class contains bonus method and it takes
int argument
So you are call bonus method and parse 45000 to that.
String name="Java lovely"; // You are define a String
name.length(); // this will return the length of name String, no need input
argument and return int length
I had used the following code to find the length
String str=strLenData.toString();
int ipLen= str.length();
return ipLen;
ipLen would return 11 every time. whatever be the actual value of strLenData. when I call toString() function, value of str: "[C#40523f80". Now I have to use char[] and i need to know the end (or length) of char[].
How do I do it?
If I understand correctly the strLenData variable is a char[]? In that case, you can just do
return strLenData.length;.
I don't think strLenData is charSequence or something. its just a regular object and may be it does't have toString() method. so toString() method of Object class gets called which just returns the HashCode value of The Objects Reference.
so make sure strLenData.toString() can be used.
ipLen is returning 11 always because you are converting an char array to String equivalent by using toString() method.
if you want to create String by an char array use.
String str = new String(strLenData);
Or if you want just want to get length of your char array use answer given by Steven.
use strLenData.length;