字符串拼接操作总结

字符串的两种定义方式

 	 String s1 = "abc" ;      // 字面量的定义方式,字符串存储在常量池中
	 String s2 =  new String("hello");     // new 对象的方式

注意事项:

  1. String被声明为final的,不可被继承。
  2. String实现了Serializable接口:表示字符串是支持序列化的。实现了Comparable接口:表示String可以比较大小。
  3. Stringjdk8及以前内部定义了final char value[]用于存储字符串数据。JDK9时改为byte[]。改变的主要原因是节省空间,因为很多字符串都是一个字节。
  4. 字符串常量池不会存储相同内容的字符串。
  5. jdk7之后将字符串常量池放到了堆中,之前是在永久代里面。

字符串拼接操作注意事项:

  1. 常量与常量的拼接结果在常量池,原理是编译期优化,常量池中不会存在相同内容的变量。拼接的字符串中只要其中有一个是变量,结果就在堆中。
  2. 变量拼接的原理是StringBuilder,如果拼接的结果调用intern()方法,根据该字符串是否在常量池中存在,分为:
    2.1 存在: 则返回字符串在常量池中的地址如果字符串常量池中
    2.2 不存在: 则在常量池中创建一份,并返回此对象的地址
      String s1 = "a" + "b" + "c";//编译期优化:等同于"abc"
      String s2 = "abc"; //"abc"一定是放在字符串常量池中,将此地址赋给s2

字符串拼接的底层操作

		String s1 = "a";
        String s2 = "b";
        String s3 = "ab";
        /*
        如下的s1 + s2 的执行细节:(变量s是我临时定义的)
        ① StringBuilder s = new StringBuilder();
        ② s.append("a")
        ③ s.append("b")
        ④ s.toString()  --> 约等于 new String("ab"),但不等价 */
        String s4 = s1 + s2;//
        System.out.println(s3 == s4);//false
        // 但是如果用final修饰了,s4+s5就相当于"a"+"b"
        final String s4 = "a";
        final String s5 = "b";
        String s6 = "ab";
        String s7 = s4 + s5;
        System.out.println(s6 == s7);//true

注意:

  • 通过StringBuilderappend()的方式添加字符串的效率要远高于使用String的字符串拼接方式!
  • 原因1:StringBuilderappend()的方式:自始至终中只创建过一个StringBuilder的对象
  • 原因2:使用String的字符串拼接方式:创建过多个StringBuilderString(调的toString方法)的对象,内存占用更大;如果进行GC,需要花费额外的时间(在拼接的过程中产生的一些中间字符串可能永远也用不到,会产生大量垃圾字符串)。

intern方法

  1. intern是一个native方法,调用的是底层C的方法字符串常量池池最初是空的,由String类私有地维护。
  2. 在调用intern方法时,如果池中已经包含了由equals(object)方法确定的与该字符串内容相等的字符串,则返回池中的字符串地址。否则,该字符串对象将被添加到池中,并返回对该字符串对象的地址。

new String()的说明

  1. new String("ab")会创建几个对象?
  • 一个对象是:new关键字在堆空间创建的
  • 另一个对象是:字符串常量池中的对象"ab"。(如果之前字符串常量池中没有“ab” 的话)
  1. new String(“a”) + new String(“b”)会创建几个对象?代码
  • 对象1:new StringBuilder()
  • 对象2: new String("a")
  • 对象3: 常量池中的"a"(如果之前字符串常量池中没有“a”的话)
  • 对象4: new String("b")
  • 对象5: 常量池中的"b"(如果之前字符串常量池中没有 “b”的话)
  • 对象6 :new String("ab"),此处注意在字符串常量池中,没有生成"ab"
  1. 特殊情况
		String s = new String("1");
        s.intern();//调用此方法之前,字符串常量池中已经存在了"1"
        String s2 = "1";
        System.out.println(s == s2);//jdk6:false   jdk7/8:false
        /*
         1、s3变量记录的地址为:new String("11")
         2、经过上面的分析,我们已经知道执行完pos_1的代码,在堆中有了一个new String("11")
         这样的String对象。但是在字符串常量池中没有"11"
         3、接着执行s3.intern(),在字符串常量池中生成"11"
           3-1、在JDK6的版本中,字符串常量池还在永久代,所以直接在永久代生成"11",也就有了新的地址
           3-2、而在JDK7的后续版本中,字符串常量池被移动到了堆中,此时堆里已经有new String("11")了于节省空间的目的,直接将堆中的那个字符串的引用地址储存在字符串常量池中。没错,字符串常量池存的是new String("11")在堆中的地址,所以s4指向了new String("11")。
         4、所以在JDK7后续版本中,s3和s4指向的完全是同一个地址。
         */
		String s3 = new String("1") + new String("1");//pos_1
		s3.intern();
		String s4 = "11";//s4变量记录的地址:使用的是上一行代码代码执行时,在常量池中生成的"11"的地址
		System.out.println(s3 == s4);//jdk6:false  jdk7/8:true
  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
### 回答1: 好的,在 shell 中可以使用两种方法来拼接字符串。 1. 使用双引号:双引号内的变量会被解析,所以可以在双引号内直接拼接字符串和变量。例如: ``` a="hello" b="world" c="$a $b" echo $c # 输出 hello world ``` 2. 使用反引号:反引号内的内容会被当作命令来执行,然后把输出的结果当作字符串来使用。例如: ``` a="hello" b="world" c=`echo "$a $b"` echo $c # 输出 hello world ``` 两种方法都可以用来拼接字符串,但是双引号通常更常用一些。 ### 回答2: 在shell脚本中,可以使用不同的方法实现字符串的拼接。 1. 使用拼接操作符 "+" 可以使用拼接操作符 "+" 来实现字符串的拼接。例如: ```shell str1="Hello," str2=" world!" result=$str1$str2 echo $result # 输出:Hello,world! ``` 2. 使用双引号 双引号可以将多个字符串拼接在一起。例如: ```shell str1="Hello," str2=" world!" result="$str1$str2" echo $result # 输出:Hello, world! ``` 3. 使用单引号 如果使用单引号,字符串将保持原样,不进行变量替换。例如: ```shell str1="Hello," str2=" world!" result='$str1$str2' echo $result # 输出:$str1$str2 ``` 4. 使用printf命令 printf命令可以使用格式化字符串将多个字符串拼接在一起。例如: ```shell str1="Hello," str2=" world!" result=$(printf "%s%s" "$str1" "$str2") echo $result # 输出:Hello, world! ``` 总结起来,shell中可以使用拼接操作符、双引号、单引号或printf命令来实现字符串的拼接。可以根据需要选择最适合的方法来进行操作。 ### 回答3: Shell字符串拼接是将两个或多个字符串连接起来形成一个新的字符串。在Shell脚本中,可以使用不同的方法来进行字符串拼接。 一种常见的方法是使用变量和字符串的拼接操作符(+),如:`result=$string1$string2`。这会将string1和string2连接起来,并将结果赋值给result变量。 另一种方法是使用引号(单引号或双引号)来拼接字符串。使用双引号可以在字符串中插入变量,使用单引号则将字符串原样输出。例如: ``` str1="Hello" str2="World" str3="$str1 $str2" str4='I love Shell' ``` 上述代码中,str3被赋值为"Hello World",str4被赋值为"I love Shell"。 除了使用拼接操作符和引号,还可以使用命令替换的方式来拼接字符串。命令替换是通过将命令的输出结果作为字符串的一部分来实现的。可以使用反引号(`)或$()来进行命令替换。例如: ``` date=`date` result=$(ls -l) ``` 上述代码中,date变量被赋值为当前的日期和时间,result变量被赋值为ls -l命令的输出结果。 此外,Shell还提供了一些特殊字符和特殊变量来辅助字符串拼接。如`\n`表示换行符,`$PWD`表示当前工作目录等。这些特殊字符和变量可以与普通字符串一起使用来构建更复杂的字符串。 综上所述,Shell字符串拼接可以通过变量和字符串的拼接操作符、引号、命令替换以及特殊字符和特殊变量等方式来实现。根据具体的需求选择合适的方法来进行字符串拼接

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值