Java-String类

  字符串广泛应用 在Java 编程中,Java 提供了 String 类来创建和操作字符串,String类在Java中可以看作对象,这也十分符合Java面向对象编程的基本特征。而其他的字符串操作类还有Java.lang.StringBuffer和Java.lang.StringBuilder。

  • Java.lang.String

  public final class String
    implements java.io.Serializable, Comparable<String>, CharSequence{}

 

  • String类型的成员变量

 

  /** String的属性值 */  
    private final char value[];

    /** The offset is the first index of the storage that is used. */
    /**数组被使用的开始位置**/
    private final int offset;

    /** The count is the number of characters in the String. */
    /**String中元素的个数**/
    private final int count;

    /** Cache the hash code for the string */
   /**String类型的hash值**/
    private int hash; // Default to 0

    /** use serialVersionUID from JDK 1.0.2 for interoperability */
    private static final long serialVersionUID = -6849794470754667710L;
    /**
     * Class String is special cased within the Serialization Stream         Protocol.
     *
     * A String instance is written into an ObjectOutputStream according to
     * <a href="{@docRoot}/../platform/serialization/spec/output.html">
     * Object Serialization Specification, Section 6.2, "Stream Elements"</a>
     */

  private static final ObjectStreamField[] serialPersistentFields = new ObjectStreamField[0];

  由上面的成员变量可以知道String类的值是final类型的,不能被改变的,所以只要一个值改变就会生成一个新的String类型对象,存储String数据也不一定从数组的第0个元素开始的,而是从offset所指的元素开始。                                              

而且,String对象中字符串主要是以字符数组的形式存储;

 

  1. String的不变性

 

//一个字符串对象创建后它的值不能改变。
String str1="hello";//创建一个对象hello,不会变;
str1+=" world!";//两个字符串对象粘粘,系统其实创建了一个新的对象,把Str1的指向改了,指向新的对象;hello就变成了垃圾;
//如果一直这样创建会影响系统的效率;要频繁的改变字符串对象的值就用StringBuffer来描述;
StringBuffer sb=new StringBuffer("hello"); sb.append("world"); sb.append("!!!");//append();不会制造垃圾,真正在改sb的值;

 

  2.对象池(String池?)

  首先要明白,Object obj = new Object();  obj是对象的引用,它位于栈中, new Object() 才是对象,它位于堆中。

  创建一个Stirng对象: String str1 = new String("abc");    Stirng str2 = "abc"; 

  虽然两个语句都是返回一个String对象的引用,但是jvm对两者的处理方式是不一样的。第一种,jvm会马上在heap中创建一个String对象,然后将该对象的引用返回给用户。第二种(不是new的),jvm首先会在内部维护的strings pool中通过String的 equels 方法查找是对象池中是否存放有该String对象,如果有,则返回已有的String对象给用户,  而不会在heap中重新创建一个新的String对象;如果对象池中没有该String对象,jvm则在heap中创建新的String对象,将其引用返回给用户,同时将该引用添加至strings pool中。

注意:使用第一种方法创建对象时,jvm是不会主动把该对象放到strings pool里面的,除非程序调用 String的intern方法。

String str1 = new String("abc"); //jvm 在堆上创建一个String对象     
Stirng str2 = "abc";     
 //jvm 在strings pool中找不到值为“abc”的字符串,因此     
 //在堆上创建一个String对象,并将该对象的引用加入至strings pool中     
 //此时堆上有两个String对象     

 if(str1 == str2){     
         System.out.println("str1 == str2");     
 }else{     
         System.out.println("str1 != str2");     
 }     
  //打印结果是 str1 != str2,因为它们是堆上两个不同的对象     
    
  String str3 = "abc";     
 //此时,jvm发现strings pool中已有“abc”对象了,因为“abc”equels “abc”     
 //因此直接返回str2指向的对象给str3,也就是说str2和str3是指向同一个对象的引用     
  if(str2 == str3){     
         System.out.println("str2 == str3");     
  }else{     
         System.out.println("str2 != str3");     
  }     
 //打印结果为 str2 == str3    

  (图片来自网络,侵删。)

  • 构造方法

  Java.lang.String对象构造方法比较多,列举如下:

    public String()
    public String(String original)
    public String(char value[])
    public String(char value[], int offset, int count)
    public String(int[] codePoints, int offset, int count)
  @Deprecated
    public String(byte ascii[], int hibyte, int offset, int count)
  @Deprecated
    public String(byte ascii[], int hibyte)
    public String(byte bytes[], int offset, int length, String charsetName) throws UnsupportedEncodingException
    public String(byte bytes[], int offset, int length, Charset charset)
    public String(byte bytes[], String charsetName) throws UnsupportedEncodingException
    public String(byte bytes[], Charset charset)
    public String(byte bytes[], int offset, int length)
    public String(byte bytes[])
    public String(StringBuffer buffer)
    public String(StringBuilder builder)

String的几个常见的构造方法

  无参数的构造方法:

public String() {
    this.offset = 0;
    this.count = 0;
    this.value = new char[0];
}

  传入一个Sring类型对象的构造方法

    int size = original.count;
    char[] originalValue = original.value;
    char[] v;
      if (originalValue.length > size) {
         // The array representing the String is bigger than the new
         // String itself.  Perhaps this constructor is being called
         // in order to trim the baggage, so make a copy of the array.
            int off = original.offset;
            v = Arrays.copyOfRange(originalValue, off, off+size);
     } else {
         // The array representing the String is the same
         // size as the String, so no point in making a copy.
        v = originalValue;
     }
    this.offset = 0;
    this.count = size;
    this.value = v;
    }

  传入一个字符数组的构造函数

public String(char value[]) {
    int size = value.length;
    this.offset = 0;
    this.count = size;
    this.value = Arrays.copyOf(value, size);
    }

  传入一个字符串数字,和开始元素,元素个数的构造函数

public String(char value[], int offset, int count) {
        if (offset < 0) {
            throw new StringIndexOutOfBoundsException(offset);
        }
        if (count < 0) {
            throw new StringIndexOutOfBoundsException(count);
        }
        // Note: offset or count might be near -1>>>1.
        if (offset > value.length - count) {
            throw new StringIndexOutOfBoundsException(offset + count);
        }
        this.offset = 0;
        this.count = count;
        this.value = Arrays.copyOfRange(value, offset, offset+count);
    }
  • 常用方法

String 类包括的方法可用于检查序列的单个字符、比较字符串、搜索字符串、提取子字符串、创建字符串副本并将所有字符全部转换为大写或小写等;

1、length() 字符串的长度
  例:char chars[]={'a','b'.'c'};
    String s=new String(chars);
    int len=s.length();

2、charAt() 截取一个字符
  例:char ch;
    ch="abc".charAt(1); 返回'b'

3、 getChars() 截取多个字符
  void getChars(int sourceStart,int sourceEnd,char target[],int targetStart)
  sourceStart指定了子串开始字符的下标,sourceEnd指定了子串结束后的下一个字符的下标。因此, 子串包含从sourceStart到sourceEnd-1的字符。接收字符的数组由target指定,target中开始复制子串的下标值是targetStart。
  例:String s="this is a demo of the getChars method.";
    char buf[]=new char[20];
    s.getChars(10,14,buf,0);

4、getBytes()
  替代getChars()的一种方法是将字符存储在字节数组中,该方法即getBytes()。

5、toCharArray()

6、equals()和equalsIgnoreCase() 比较两个字符串

7、regionMatches() 用于比较一个字符串中特定区域与另一特定区域,它有一个重载的形式允许在比较中忽略大小写。
  boolean regionMatches(int startIndex,String str2,int str2StartIndex,int numChars)
  boolean regionMatches(boolean ignoreCase,int startIndex,String str2,int str2StartIndex,int numChars)

8、startsWith()和endsWith()  startsWith()方法决定是否以特定字符串开始,endWith()方法决定是否以特定字符串结束

9、equals()和==
  equals()方法比较字符串对象中的字符,==运算符比较两个对象是否引用同一实例。
  例:String s1="Hello";
    String s2=new String(s1);
    s1.eauals(s2); //true
    s1==s2;//false

10、compareTo()和compareToIgnoreCase() 比较字符串

11、indexOf()和lastIndexOf()
  indexOf() 查找字符或者子串第一次出现的地方。
  lastIndexOf() 查找字符或者子串是后一次出现的地方。

12、substring()  它有两种形式,第一种是:String substring(int startIndex)
         第二种是:String substring(int startIndex,int endIndex)

13、concat() 连接两个字符串

14 、replace() 替换
  它有两种形式,第一种形式用一个字符在调用字符串中所有出现某个字符的地方进行替换,形式如下:
  String replace(char original,char replacement)
  例如:String s="Hello".replace('l','w');
  第二种形式是用一个字符序列替换另一个字符序列,形式如下:
  String replace(CharSequence original,CharSequence replacement)

15、trim() 去掉起始和结尾的空格

16、valueOf() 转换为字符串

17、toLowerCase() 转换为小写

18、toUpperCase() 转换为大写

更多方法:http://www.runoob.com/java/java-string.html

 

连接字符串的几种方式

1、最直接,直接用+连接

     String a = new String("bb");
     String b = new String("aa");
     String c =  a + b;

 

 

 2、使用concat(String)方法

      String a = new String("bb");
      String b = new String("aa"); 
      String d = a.concat(b);

 

 

3、使用StringBuilder

 String a = new String("bb");
 String b = new String("aa");
     
StringBuffer buffer = new StringBuffer().append(a).append(b);

    第一二中用得比较多,但效率比较差,使用StringBuilder拼接的效率较高。

  • String

 

 

 

 

 

  

posted on 2017-09-02 14:23  幼儿猿  阅读(130)  评论(0)    收藏  举报

导航