zoukankan      html  css  js  c++  java
  • Java复习3.变量.常量.String.

    Java 中的变量常量数据类型 20131004

    前言:

             还是国庆节,无聊的很,就没事复习点Java的知识,其实C/C++基本上是现在大型企业面试的语言,但是多学习点Java是没有坏处的,而且,将来工作的话,不可能只会一门C++就不管了,现在的开发工程师都是会使用C++和Java两者都是精通的。

    话说国庆节结束之后,有一大群公司来招聘,还很多是IT的,那我是去呢,还是去呢?首先声明,我去的话绝对不是篡你们的,可能是考虑到自己的工作地点吧,我想去工作的地方是成都,至于为什么,就是喜欢了,也说不出来为什么(你信吗?)

    说道正题,本文是关于常见的Java一些知识点总结,重点是Java中的String类的知识。Java中的String研究了好久好久,收获蛮大的。

    1.常量

             final String str =”yang”; 不可以改变,如果不加上static,就是存储在stack中的一个常量;其中的yang是在String Pool中的,str指向的是String Pool在内存中的一个副本的地址。

    2.变量

             局部变量:存储在stack中,当超出变量作用域的时候,自动清退;

             全局变量:其实在Java中没有全局变量的概念,只是他们比局部变量的范围大了一点,放在程序的类中,作为类的属性,对于使用static修饰的类的静态变量,可以使用ClassName访问,也可以使用对象访问,但是访问权限应该是public。

    3.数据类型的大小

             只有char和C++不同,在Java中一个char类型的数据大小是2个byte

    4.标识符和关键字

             可以使用$开头

    5.运算符(我们不常见的)

             ~按照位取反

             & 按位与

             |按位或

             ^按位异或

             >> 右移

             >>> 右移使用0填充

             << 左移

                       byte a = 7;

                       System.out.print(a);

                       a = (byte) (a>>1);

                       System.out.print(a);

                       a = (byte) (a<<1);

                       System.out.print(a);

    6运算符的优先级

             ! > && > ||

             [] > ()

    7.Java中的字符串

             7.1字符串的初始化:

             String a = new String();

             a=”yangtengfei”;

             或者String a = new String(“yangtengfei”);

             String是不可以改变的数据类型,一旦生成就不可以对字符串内容进行修改。这样的好处就是当一个对象需要被多个线程共享的时候,并且访问频繁,可以省略同步和锁的等待时间,提高系统的性能。

             String a = new String(“yangtengfei”);

             这句代码实际上是生成了两个String对象,一个是”yangtengfei”直接的字符串对象,另一个就是new String返回的空字符串对象。

             我们研究一下JVM对于字符串操作的机制:

             对于Java的直接字符串对象(String a = “yangtengfei”),JVM会将字符串保存在缓冲池中,同时在内存(在堆中)中有一个副本,变量a指向的是该副本,也就是当第一次使用该直接字符串量的时候,JVM会将他们放字符串缓冲池中;当再次使用该直接字符串量的时候,,无需在创建一个字符串,只需要引用变量执行缓冲池中已经存在字符串的即可。

             但是对于String b = new String(“yangtengfei”); 通过new构造器生成的对象都需要在内存中(堆中)开辟新的空间,分配新的地址空间给该对象,但是在缓冲池中依旧是这个对象的引用。

    String a = new String("yangtengfei");

    String b = new String("yangtengfei");

    String c = "yangtengfei";

    String d = "yangtengfei";

     

    System.out.println("a==b:" + (a==b)); // false 堆中不用的引用

    System.out.println("a==c:" + (a==c));//false 一个是堆新建的,另一个不是

    System.out.println("c==d:" + (c==d));//true 都是对堆中同一个对象的引用

    System.out.println("a==c.intern():"+ (a.intern()==c.intern()));

    System.out.println("a.intern()==b.intern():"+ (a.intern()==b.intern()));

    其中intern返回的是对象在String Pool中的引用,他们这些字符串中都是同一个对象,但是在内存中,yangtengfei字符串是在堆中,只是new的对象都是重新分配内存,而直接字符串都是在堆中的同一个引用。最终都是String Pool中的同一个字符串. (有点晕菜的感觉,给你一张图解释一下就明白了).

     

             (图片原创)

             字符串初始化的多种情况:

             String a = “yang”+ “teng” + “fei”;这个过程中,创建的字符创对象有几个:只有一个,为什么呢 ?

             看一下JVM编译器的编译原理:

             如果一个字符串是连接表达式,并且可以在编译期间确定下来的话,那么JVM编译器会在编译的时候计算字符串的值,并且将它指向String Pool中的值;但是如果字符串连接的时候使用了方法,或者是变量,那么就只能够等到运行期间才可以知道字符串的值,在编译期间是无法得知的,这样的话就无法利用String Pool

             对于String Pool,只有在编译期间确定的字符串才会保存在缓冲池中,而运行期间确定的字符串是不会在缓冲池中保存的

             String name = “yang”; name = name + “tengfei”; 这两句代码创建的字符串有几个,三个,一个是yang,一个是 “tengfei”,最后一个是 “yangtengfei”, 这三个字符串是在内存中,更精确地说实在堆中的,而在栈中只有一个变量就是name,指向不同的字符串。

             但是在String Pool中存在的字符串只有yang 和tengfei, 而对于字符串 yangtengfei 是不会缓存在String Pool中的,因为是在运行期间才确定的字符串。这样在Heap中会生成垃圾,会被GC自动回收。

             使用字符串缓冲池,就是为了节省内存,提高资源的利用率,在缓冲池中的数据是不会被GC回收的,基本上就是常驻内存,所以过多的使用String Pool可能会造成内存溢出(这里不是内存泄露,而是占用了大量的内存空间导致内存爆掉了)。

            

    StringBuffer和StringBuilder去操作可变的字符串的时候,不会在新建一个字符串对象,引用的是同一个字符串对象,减少了字符串的弊端。StringBuilder是线程不安全的,适合于单线程的程序,StringBuffer是线程安全的,因为其中的方法大部分添加了synchronized机制,但是降低了他的效率。

                      StringBuilder sb = new StringBuilder();

          System.out.println(System.identityHashCode(sb));

          sb.append("yang");

          System.out.println(System.identityHashCode(sb));

          sb.append("teng");

          System.out.println(System.identityHashCode(sb));

    追梦的飞飞

    于广州中山大学 20131004

    HomePage: http://yangtengfei.duapp.com

  • 相关阅读:
    类在编写过程中的一些注意事项
    SDUT 2893-B(DP || 记忆化搜索)
    Microsoft.AlphaImageLoader滤镜解说
    解决网页版权符号模糊不清
    oninput,onpropertychange,onchange的使用方法和差别
    VB.net数据库编程(03):一个SQLserver连接查询的简单样例
    使用WinSetupFromUSB来U盘安装windowsXP(不使用win PE系统)
    ActivityManager
    IP协议
    jni编译non-numeric second argument to `wordlist' function错误
  • 原文地址:https://www.cnblogs.com/hbhzsysutengfei/p/3409511.html
Copyright © 2011-2022 走看看