java基础-1-数据类型,编码,运算与流程控制

1 基本信息

  • 2个保留字:goto、const

  • 3个直接量:true、false、null

  • 标识符:字母、中文、符号下划线_或者以符号$开头,符号仅可能有下划线和$

  • 注释:单行注释如// ...,块或多行注释如/ ... /,文档注释如/* ... /,用于提取信息,如作者@author,参数@param;生成文档注释的命令:javadox xxx.java


2 基本数据类型与包装类

  • 包装类是对基本数据类型的包装,使其具有面向对象的特征(封装,继承,多态),提供属性和操作方法,默认值为null

基本数据类型/包装类:8种表示范围字节(1字节 = 8位)
byte / Byte 字节-128 - 1271

1 byte = 8 bit

1 KB = 1024 byte

1 MB = 1024 KB

1 GB = 1024 MB

short / Short 短整-2^15 - 2^15-12
int /Integer  整数的默认类型-2^31 - 2^31-14

1、与2/8/16进制的转换:Integer. toBinaryString(value) /toOctalString(value) /toHexString(value)

2、转为任意进制:Integer.toString(value, n)

long / Long 长整8

默认值0L

BigInteger:操作大整数工具类,包含了常用的数学方法

float / Float 单精度浮点类型4默认值0.0f/F
double / Double 双精度浮点类型8

浮点数默认类型

浮点数采用科学计数法,丢失数据,即1 * 0.1 != 0.1;作比较时转为>=或<=,如float EP = 0.00000001F;if (testNumber >= -EP) && (testNumber <= EP);则认为它们等值

BigDecimal:用于金融方面确保精度的工具类

boolean / Boolean 布尔1

默认值false

参与字符串运算时被提升为字符串

char / Character 字符与编码相关;Unicode编码占2字节

默认值'\0'

可赋值为汉字

不能使用双引号

特殊字符如换行'\n',制表'\t'

可直接使用Unicode值表示,如'\uXXX';也可以表示0-65535内的整数

  • 自动类型转换/提升

    • 转换条件:

      • 表示范围低的 -> 表示范围高的,会发生自动类型转换

      • 类型要兼容,数值类型(整数和浮点数)兼容

    • 声明long,float,double类型数据时,当值在int范围内(值的取值范围限制且没有小数)时可省略后缀,否则必加后缀;如long l = 10L;等同于long l = 10;

    • 表达式结果的类型,为表达式中表示范围最大的类型:如double类型与int类型运算,得到的值自动提升为double型

    • 表达式自动类型提升:对byte/char/short参与的表达式运算,自动提升结果为int型,如byte + short = int;注意返回类型不兼容则报错

      int a = 5;
      int b = 2;
      double e = 5;
      System.out.println(a / b); // 最大类型为int,结果值为int,即输出2
      System.out.println(e / b); // 最大类型为double,结果为double,即输出2.5
      double c = a / b;
      System.out.println(c); // 最大类型为int,结果为int,即a / b输出2,将2赋值为double,所以输出2.0;int型值赋值给double型,即自动类型转换
      double d = a * 1.0 / b;
      System.out.println(d); // 最大类型为double(通过 *1.0操作实现),结果为double,即a * 1.0 / b输出2.5,将其赋值给d,输出2.5
      
      // =========================================================================
      byte a = 1; byte b = 2;
      byte c = 1 + 2; // 正确,此时的1和2就是byte范围内的1和2
      byte d = a + b; // 错误,右边运算结果被提升为int类型,不能返回给byte类型的d
      a += 1; // 正确,+= 类似于 =,是赋值运算/一次运算
      a = a + 1; // 错误,右边为算数运算,然后赋值,为二次运算,结果自动提升为int类型,不能赋值给byte类型的a

  • 强制类型转换:将一种数据类型强行转为另一种数据类型;不一定必须是表示范围高的转为表示范围低的才用,如自动类型转换也可以显式写出转换类型来让它强制转换;因为会丢失数据精度,慎用

     int i = 233;
     byte b = (byte)i; // 输出b为-23;byte范围为8位,丢失int范围32位的前24位,最高位为符号位,233的二进制右边8位的最高位为1,表示负数,负数以补码形式存储,后7位-1后转为反码在转为源码为-23

  • 自增,自减运算符:

     /**
      * 重点:
      *  i++/i--是在自身上变化,即增减操作在局部变量表中进行,其他操作都在操作数栈中完成
      *  i++即自增表示变量自己增加,不执行入栈操作;同理自减;而++i需要先执行入栈后在栈中完成++;最后将栈中值取出赋给局部变量
      *  =赋值最后执行;=右边的值从左到右依次入栈,然后根据运算符执行优先级,临时结果也存入栈中
      */
     private static void doAdd() {
         int i = 1; // 局部变量i=1;执行入栈i的值,栈中存储1;可以理解为变量i指向栈中的值1
         i = i++;  // 执行i++,局部变量i=2;然后执行赋值,将栈中的1赋给i,最终i=1;可以理解为变量i指向自身,于是将自身指向的栈中的值赋予变量i(赋值:将变量指向的栈中的值赋予变量)
         // i++; 注意区别于这一行代码:局部变量i=1,执行入栈i,栈中存储1,然后执行i++,局部变量i=2,没有赋值,最终i=2
         int j = i++; // 局部变量j默认=0,i=1,执行入栈i的值,栈中存储1;然后计算i++,局部变量i=2;然后执行赋值,将栈中的1赋给j,j=1
         // 注意此时的局部变量i没有被栈中i赋值,所以最终i=2
         int k = i + ++i * i++; // 局部变量k=0,i=2;依次入栈执行,从底到顶为i=2,执行++i即i=3,执行i++即i=3,最终栈内为2,9;然后局部变量i执行++即i=4
         // 然后将栈中元素2+9赋值给k,最终k=11;i没有被赋值,i=4
         System.out.println(i +"," + j +"," + k);
     }

  • 特殊的,char类型字符与int类型的转换:

     char c = '8';
     System.out.println(c); // 输出 8
     int i = c; // 自动类型转换
     System.out.println(i); // 输出 c的ASCII码,即56
     System.out.println(c - '0'); // 输出int类型的8,即通过操作转为了int型(用instanceof Integer判断,注意instanceof不能用于基本数据类型的判断)
     // 输出打印26个字母:'a'+1得到'b',最终stringBuffer为26个字母字符串
     for (int i = 0; i < 26; i++) {
         char c = (char)('a' + i);
         stringBuffer.append(c);
     }

  • 装箱

     Integer i
         = new Integer(1); // 传入基本数据类型到构造器实现装箱
         = new Integer("1"); // 传入可转为数值类型的字符串到重载的构造器实现装箱,可能引发NumberFormatException
         = Integer.valueOf(1); // 传入基本数据类型到静态方法
         = Integer.valueOf("1"); // 同理,重载
         = 1; // JDK1.5后的进行自动装箱,编译器实际执行=Integer.valueOf(1);为了提高效率,Java设计针对-128 -127之间的数据进行缓存到一个数组中,类似常量池,每次使用时从此处获取;而超出部分虽然也写作自动装箱,但底层实现是转为new对象;所以比较的时候需要判断底层实现的方式:
     Integer a = (-128 - 127);
     Integer b = (-128 - 127); // a == b 返回true,它们都是缓存中的那个数
     Integer c = new Integer(-128 - 127); // a != c,b != c,c指向新new的一个对象
     Integer d = 200; 
     Integer e = 200; // d != e,它们不在缓存范围内,因此转为指向各自new出的对象
    List<Integer> list = new ArrayList<>();
    list.add(1); // 集合存储基本数据类型的数据时,存储的是对应的包装类;做add()时发生自动装箱
    list.get(0); // 返回Integer,也可以用int来接收
    
     ​
     // 包装类还提供了系列工具方法,如数据比较compare(基本数据类型1, 基本数据类型2),返回1,0或者-1
     i += 1; // 包装类完成一次运算,经过了先拆箱,完成int的+运算后,再装箱的过程

  • 拆箱

     int i
         = a; // 先定义Integer a;自动拆箱,编译器实际执行了下面的方法
         = a.intValue(); // 其他类型同理,如floatValue()

  • 与字符串的转换:

    • 基本数据类型/包装类转为字符串:

      1. 变量/对象.toString()

      2. 使用String的静态方法String.valueOf(变量)

      3. 直接使用连接符 + 号

    • 字符串转为基本数据类型/包装类,注意字符串须满足是可转为数值的:

      1. parseXXX(): 包装类的静态方法解析字符串,如Integer.parseInt(string)

      2. 使用构造器装箱


3 进制

  • 二进制最高位表示符号位,JDK1.7后以0b或0B开头;八进制以0开头;十六进制以0x或0X开头,10-15用不区分大小写的a-f表示

  • 二进制与十进制的转换

    • 二进制数与权的对应关系:个位对应2的0次幂,十位对应2的1次幂,百位对应2的2次幂,。。。小数点后一位对应2的-1次幂,依次类推;2的X次幂即为权

    • 加权系数展开式:以每一位上的数(0或1) * 权,然后按权相加求和

      • 二进制 1011.01 = 1X2^3 + 0X2^2 + 1X2^1 + 1X2^0 + 0X2^-1 + 1X2^-2 = 8+0+2+1+0+0.25 = 11.25 十进制

      • 十进制 整数部分用商连续除以2并记录余数,逆序排列,如89的余数1001101,直到最后1除以2,于余1;小数部分用小数连续乘以2并记录整数,顺序排列,如0.625,余数分别为0.101


4 字符集与编解码

  • 编码encode:字符转字节;解码decode:字节转字符;通过码表对应

  • ASCII字符集:7位表示,1位存储(提高读写效率):

    • 数字0 - 9:char >= 48 && char <= 57,或者char == '0/1/2/3...'

    • A - Z:char >= 65 && char <= 90,或者char == 'A/B/C...'

    • a - z:char >=97 && char <= 122,或者char == ‘a/b/c...

  • ISO-8859-1:单字节编码,0-255,仅用于英文,即一个字母字符为一个字节

  • GB2312(简体) -> GBK(扩展到繁体):双字节编码,汉字国标码,英文兼容ISO-8859-1;即一个中文字符为两个字节,英文字符一个字节

  • Unicode:一般为定长双字节编码,即所有字符都是两个字节,统一,但不方便传输和存储,16进制方式;Java常用

  • UTF:不定长编码,一般英文1字节,汉字3字节

    • UTF-8:1-6个字节变长存储

    • UTF-32:4字节定长存储

    • UTF-16:介于两者之间,2或者4字节可变长,可定长存储

  • 解决乱码:byte[] bytes = string.getBytes()获取字节数组;该字节数组默认字符集与项目一致;可另设置字符集,如bytes = string.getBytes("GBK");反之解码,通过String类的重载构造器指定,如string = new String(bytes, 0, bytes.length, "utf8");指定的长度不够或指定的编解码不统一,都可能出现乱码

  • 详细讲解:关于JAVA字符编码:Unicode,ISO-8859-1,GBK,UTF-8编码及相互转换 - 海米傻傻 - 博客园


5 运算符

  • 算数运算:+ 、- 、* 、 / 、%

    • 符号 + 还可用作字符串连接

    • 符号 - 还可用作求负运算

    • 符号 / 用于整数,结果求模,即舍去余数,结果为整数;用于浮点数,除数可以为0或0.0,结果为浮点数

    • 符号 % 用于整数,结果求余,即只要余数,结果为整数;用于浮点数???????????

  • 比较运算:==、!=、>、<、>=、<=;true == false返回false

  • 逻辑运算!非、&&与、||或、^异或

    • !:取反

    • &&:同为true,则结果为true,否则为false

    • ||:同为false,则结果为false,否则为true

    • 短路特性:短路后,后面的表达式不再执行,直接舍弃

    • ^:同则false,不同则true

    • 优先级依次降低,如false || true && !false,优先!false为true,再true&&true为true,最后false||true为true

  • 位运算:针对二进制整数(包含提升为int的byte,char,short);所移位数超过范围时,先取余,如int为4字节共32位,如果移动33位,等于移动1位

    • ~:按为取反

    • &:11得1,否则得0

    • |:00得0,否则得1

    • ^:同得0,不同得1(同逻辑运算,1看做true,0看做false)

    • <<:移除左边高位,右边以0填充,等同于 *2的移动次幂

    • 符号>>:左边以原数的符号位填充,等同于 /2的移动次幂

    • 无符号>>>:


6 条件语句-流程控制

  • switch...case:

    • switch的条件支持:byte,char,short,int,enum枚举(JDK1.5),String非缓冲字符串(JDK1.7);enum最终会被转换为int序号;String通过hashcode计算,也得出一个int范围内数值,以此适应switch

    • 条件与任意case都不匹配时,执行default

    • default语句可在任意位置;当位于首行时,无论条件与case是否匹配,程序都会执行default直到break出现

    • 条件不支持的类型:

      • long类型:switch编译时用到两个操作指令,tablesswitch和lookupswitch,这两个指令运行在int指令之下,所以超过int范围的数不被支持

      • 浮点型:浮点型精度不确定

  • for:

    • 初始变量可以多个,但一定同类型

    • break:结束循环;当需要直接结束外层循环时,循环外声明一个特殊标识符,如end: 来标识某层循环,通过break end: 来结束该层循环

    • continue:结束这一轮循环,即后面的代码不再执行,开始执行下一轮循环;可配合标志符

    • foreach:增强for循环, 自动遍历数组或集合的元素;for (type name: Array/Collection) ,底层为简化了的迭代器 ;无需长度和索引,且自动迭代,一次后结束循环;不适用于修改元素值

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值