Home  >  Article  >  Java  >  Java Improvement (Thirteen) -----String

Java Improvement (Thirteen) -----String

黄舟
黄舟Original
2017-02-10 11:22:301099browse

It can be proved that string operation is the most common behavior in computer programming.


# 1. String

First of all, we must make it clear that String is not a basic data type, but an object, and it is an immutable object. If you look at the source code, you will find that the String class is final (of course it cannot be inherited), and by looking at the JDK documentation, you will find that almost every operation that modifies a String object actually creates a new String object.

​​ The string is an object, so before initialization, its value is null. It is necessary to mention "", null, new String() here. The difference between the three. null means that the string has not been new yet, which means that the reference to the object has not been created yet, and no memory space has been allocated to it. However, "" and new String() indicate that it has been new, but it is empty internally, but it has been created. A reference to an object requires allocation of memory space. For example: an empty glass, you can't say there is nothing in it, because there is air inside, of course you can also make it a vacuum, null and " ", the difference between new String() is like vacuum and air.

There is a very special place in the string, that is the string pool. Whenever we create a string object, we will first check whether there is a string with equal face value in the string pool. If there is, it will not create it and directly put the reference to the object back in the string pool. If not, then Create and then put it into the string pool and return a reference to the newly created object. This mechanism is very useful because it can improve efficiency and reduce memory space usage. Therefore, it is recommended to use direct assignment (i.e., when using strings). String s="aa"), a new String object (i.e. String s = new String("aa")).

The use of strings is nothing more than these aspects:

## ​ 1. String comparison

equals() ------ Determine whether the contents are the same.

         compareTo() ------ Determine the size relationship of strings.

         compareToIgnoreCase(String int) ------Ignore the case of letters when comparing.

          == ------Determine whether the content and address are the same.

equalsIgnoreCase() ------ Determine whether the contents are the same while ignoring case.

            reagionMatches() ------ Compares whether part of the string is the same (please refer to the API for details).

2. String search

                      charAt(int index) ------Returns the character at the specified index index position, the index range starts from 0.

## Indexof (String STR) ------ Start with the string to retrieve STR, and return to the first appearing position, without returning to -1 .

         indexOf(String str, int fromIndex);------Retrieve str starting from the fromIndex-th character of the string.

         lastIndexOf(String str)------Find the last occurrence position.

##         

lastIndexOf(String str, int fromIndex)----Find the position of the last occurrence from the fromIndex-th character of the string.

                starWith(String prefix, int toffset)-----Test whether the substring of this string starting from the specified index starts with the specified prefix.

         starWith(String prefix)------Test whether this string starts with the specified prefix.

            endsWith(String suffix)------Test whether this string ends with the specified suffix.

3. String interception

public String subString(int beginIndex)------returns a new string, which is a substring of this string.

##               public String subString(int beginIndex, int endIndex)------The returned string is the string starting from beginIndex to endIndex-1.

4. String replacement

                                  4. String replacement

                     (char oldChar, char newChar).

##          public String replace(CharSequence target, CharSequence replacement)------Replace the original etarget subsequence with the replacement sequence and return a new string.

         public String replaceAll (String regex, String replacement)------Use regular expressions to match strings. Note that the first parameter of replaceAll is a regular expression, and I have suffered greatly from it.

5. For more methods, please refer to API


# 2. StringBuffer

StringBuffer and Strings are all used to store strings, but due to their different internal implementations, the ranges they use are different. For StringBuffer, when it processes a string, if it modifies it, it does not It does not generate a new string object, so it is better than String in terms of memory usage.

        

In fact, when it comes to using methods, many of the methods of StringBuffer are similar to those of the String class, and the functions they represent are almost exactly the same, except that StringBuffer modifies itself when it is modified. , while the String class generates a new object, which is the biggest difference between them.

​​

At the same time, StringBuffer cannot be initialized using =. It must generate a StringBuffer instance, which means you must initialize it through its construction method. ##​​

In terms of using StringBuffer, it focuses more on changes to strings, such as appending, modifying, and deleting. The corresponding methods are:

1. append(): Append the specified content to the end of the current StringBuffer object, similar to the connection of strings, where the content of the StringBuffer object will change.

2. Insert: This method mainly inserts content into the StringBuffer object.

3. delete: This method is mainly used to remove the content in the StringBuffer object.


######

                3. StringBuilder

##                                       StringBuilder is also a variable string object. The difference from StringBuffer is that it is thread-unsafe. Based on this, its speed is generally faster than StringBuffer. Like StringBuffer, the main operations of StringBuider are also the append and insert methods. Both methods effectively convert the given data into a string and then add or insert the characters of that string into the string generator.

##        The above just briefly introduces String, StringBuffer, and StringBuilder. In fact, for these three, we should focus more on the differences they only see. Only by clarifying The difference between them enables you to use them better.


##4. Use String, StringBuffer, correctly StringBuilder

##Let’s look at the following table first:


##      
I’m not very clear about whether String is thread-safe here. The reason: String is immutable, all It is impossible to change its value through any operation. It is hard to say whether there is thread safety? But if you insist on whether threads are safe, because the content is immutable, it is always safe.

​​ In terms of use, since String needs to generate a new object every time it is modified, it is best to choose StringBuffer or StringBuilder for strings whose content often needs to be changed. For StringBuffer, each operation is performed on the StringBuffer object itself, and it does not generate new objects, so StringBuffer is particularly suitable for situations where the string content changes frequently.

 ​ But not all String operations will be slower than StringBuffer. In some special cases, the concatenation of String strings will be parsed by the JVM into StringBuilder object concatenation, in this case String is faster than StringBuffer. Such as:

String name = ”I ” + ”am ” + ”chenssy ” ;

##StringBuffer name = new StringBuffer(”I ”).append(” am ”).append(” chenssy ”);

##For these two method, you will find that the first method is much faster than the second method, and the advantage of StringBuffer is lost here. The real reason is that the JVM has done some optimization. In fact, String name = "I" + "am" + "chenssy"; in the eyes of the JVM, it is String name = "I am chenssy"; this way, for the JVM, It really doesn’t take any time. But if we add a String object to this, the JVM will construct the String object according to the original specifications.

        The following is a summary of the usage scenarios of these three (reference: "Writing Quality Code: 151 Suggestions for Improving Java Programs"):

         1. String: The String class can be used in scenarios where strings do not change frequently, such as: declaration of constants, a small number of variable operations, etc.

          2. StringBuffer: If you frequently perform string operations (splicing, replacement, deletion, etc.) and run in a multi-threaded environment, you can consider Use StringBuffer, such as XML parsing, HTTP parameter parsing and encapsulation, etc.

##        3. StringBuilder: If you frequently perform string operations (splicing, replacement, deletion, etc.) and run in a multi-threaded environment, you can consider Use StringBuffer, such as assembly of SQL statements, JSON encapsulation, etc. (It seems that I also use |StringBuffer for these two).

For more information about the differences between them, please refer to: http://www.php.cn/. I won’t add any unnecessary unnecessary unnecessary fuss.

      5. String splicing method

​​​ For strings, we often need to assemble them. Three assembly methods have been added in java: +, concat() and append() methods. What is the difference between these three? Let’s look at the following example first:

public class StringTest {
    
    /**
     * @desc 使用+、concat()、append()方法循环10W次
     * @author chenssy
     * @data 2013-11-16
     * @param args
     * @return void
     */
    public static void main(String[] args) {
        //+
        long start_01 = System.currentTimeMillis();
        String a = "a";
        for(int i = 0 ; i < 100000 ; i++){
            a += "b";
        }
        long end_01 = System.currentTimeMillis();
        System.out.println("  +   所消耗的时间:" + (end_01 - start_01) + "毫米");
        
        //concat()
        long start_02 = System.currentTimeMillis();
        String c = "c";
        for(int i = 0 ; i < 100000 ; i++){
            c = c.concat("d");
        }
        long end_02 = System.currentTimeMillis();
        System.out.println("concat所消耗的时间:" + (end_02 - start_02) + "毫米");
        
        //append
        long start_03 = System.currentTimeMillis();
        StringBuffer e = new StringBuffer("e");
        for(int i = 0 ; i < 100000 ; i++){
            e.append("d");
        }
        long end_03 = System.currentTimeMillis();
        System.out.println("append所消耗的时间:" + (end_03 - start_03) + "毫米");
    }
}

------------
Output:
  +   所消耗的时间:19080毫米
concat所消耗的时间:9089毫米
append所消耗的时间:10毫米



##

public class StringTest {    
    /**
     * @desc 使用+、concat()、append()方法循环10W次
     * @author chenssy
     * @data 2013-11-16
     * @param args
     * @return void     */
    public static void main(String[] args) {        //+
        long start_01 = System.currentTimeMillis();
        String a = "a";        for(int i = 0 ; i < 100000 ; i++){
            a += "b";
        }        long end_01 = System.currentTimeMillis();
        System.out.println("  +   所消耗的时间:" + (end_01 - start_01) + "毫米");        
        //concat()
        long start_02 = System.currentTimeMillis();
        String c = "c";        for(int i = 0 ; i < 100000 ; i++){
            c = c.concat("d");
        }        long end_02 = System.currentTimeMillis();
        System.out.println("concat所消耗的时间:" + (end_02 - start_02) + "毫米");        
        //append
        long start_03 = System.currentTimeMillis();
        StringBuffer e = new StringBuffer("e");        for(int i = 0 ; i < 100000 ; i++){
            e.append("d");
        }        long end_03 = System.currentTimeMillis();
        System.out.println("append所消耗的时间:" + (end_03 - start_03) + "毫米");
    }
}------------Output:  +   所消耗的时间:19080毫米
concat所消耗的时间:9089毫米
append所消耗的时间:10毫米

It can be seen from the above running results that append() is the fastest, followed by concat() and + is the slowest. Please see the breakdown below for the reasons:


##​​ (1)+method to splice strings

##                                                                                                                                                                                                                                                   We know that the compiler optimizes +, it is processed using the append() method of StringBuilder. We know that the speed of StringBuilder is StringBuffer is faster, but why does it still run at the same speed? Mainly because the compiler uses the append() method to append and convert it into a String with toString(). That is to say, str +=”b” is equivalent to

str = new StringBuilder(str).append("b").toString();

           

The key reason why it is slow is that new StringBuilder( ) and toString(), 100,000 StringBuilder objects are created here, and they need to be converted into String each time. Is it not slow?

(2) concat() method to splice strings    

public String concat(String str) {
    int otherLen = str.length();
    if (otherLen == 0) {
        return this;
    }
    char buf[] = new char[count + otherLen];
    getChars(0, count, buf, 0);
    str.getChars(0, otherLen, buf, count);
    return new String(0, count + otherLen, buf);
    }


##     This is the source code of concat(), it looks like It is a digital copy form. We know that array processing is very fast, but because the method ends up like this: return new String(0, count + otherLen, buf); this also creates 10W string objects. This is the root cause of its slowness.


(3) append() method to splice strings

public synchronized StringBuffer append(String str) {    super.append(str);        return this;
    }

The append() method of StringBuffer is to directly use the append() method of the parent class AbstractStringBuilder. The source code of this method is as follows:

public AbstractStringBuilder append(String str) {
    if (str == null) str = "null";
        int len = str.length();
    if (len == 0) return this;
    int newCount = count + len;
    if (newCount > value.length)
        expandCapacity(newCount);
    str.getChars(0, len, value, count);
    count = newCount;
    return this;
    }


Similar to the concat() method, it also processes character arrays. Lengthen and then copy, but please note that it does not return a new string in the end, but returns itself. In other words, during this 100,000-time loop, it does not generate a new string object.

​​ Through the above analysis, we need to choose the appropriate string splicing method in the right place, but we do not necessarily have to choose append() and concat( ) method, the reason is that + according to our programming habits, we will only consider using the append() and concat() methods if it can really help the efficiency of our system. At the same time, I really don’t have any idea. Used the concat() method.

The above is the content of Java Improvement Chapter (13)-----String. For more related content, please pay attention to the PHP Chinese website (www.php.cn)!

Statement:
The content of this article is voluntarily contributed by netizens, and the copyright belongs to the original author. This site does not assume corresponding legal responsibility. If you find any content suspected of plagiarism or infringement, please contact admin@php.cn