【Java基础知识 4】Java数据类型之间的转换、运算符

阿里云国内75折 回扣 微信号:monov8
阿里云国际,腾讯云国际,低至75折。AWS 93折 免费开户实名账号 代冲值 优惠多多 微信号:monov8 飞机:@monov6

  本文已收录专栏

🌲《Java进阶之路》🌲


目录

🌴基本数据类型

🍃01、布尔

🍃02、byte

🍃03、short

🍃04、int

🍃05、long

🍃06、float

🍃07、double

🍃08、char

🌴类型转换

🍃01、强制类型转换

🍃02、自动类型转换

🍃03、什么时候会发生类型转换       

🌲引用数据类型

🌲Java 运算符​编辑

🍐01、算数运算符

🍐02、关系运算符

🍐 03、位运算符

🍐04、逻辑运算符

🍐05、赋值运算符

🍐06、三元运算符

流程控制语句


🌴基本数据类型

Java 是一种静态类型的编程语言这意味着所有变量必须在使用之前声明好也就是必须得先指定变量的类型和名称Java数据类型分类如下

 一个变量可以是局部变量、成员变量、静态变量

局部变量使用前必须初始化否则会使程序不可控制由于我们经常会忘记使用前初始化so基本上所有人都要求在定义的时候就初始化赋值否则不赋值直接使用编译器不通过。

 当变量是成员变量时可以不初始化因为会给默认值。

 bit是最小的存储单位相信只要接触过计算机就应该都知道二进制二进制的一位就是1比特0/1

通常来说一个英文字符是一个字节一个中文字符是两个字节。字节与比特的换算关系是1 字节 = 8 比特。再往上的单位就是 KB并不是 1000 字节因为计算机只认识二进制因此是 2 的 10 次方也就是 1024 个字节。

🍃01、布尔

布尔boolean仅用于存储两个值true 和 false也就是真和假通常用于条件的判断。代码示例

boolean flag = true;

🍃02、byte

byte 的取值范围在 -128 和 127 之间包含 127。最小值为 -128最大值为 127默认值为 0。

在网络传输的过程中为了节省空间常用字节来作为数据的传输方式。代码示例

byte a = 10;
byte b = -10;

🍃03、short

short 的取值范围在 -32,768 和 32,767 之间包含 32,767。最小值为 -32,768最大值为 32,767默认值为 0。代码示例

short s = 10000;
short r = -5000;

🍃04、int

int 的取值范围在 -2,147,483,648-2 ^ 31和 2,147,483,6472 ^ 31 -1含之间默认值为 0。如果没有特殊需求整型数据就用 int。代码示例

int a = 100000;
int b = -200000;

🍃05、long

long 的取值范围在 -9,223,372,036,854,775,808(-2^63) 和 9,223,372,036,854,775,807(2^63 -1)含之间默认值为 0。如果 int 存储不下就用 long整型数据就用 int。代码示例

long a = 100000L; 
long b = -200000L;

为了和 int 作区分long 型变量在声明的时候末尾要带上大写的“L”。不用小写的“l”是因为小写的“l”容易和数字“1”混淆。


🍃06、float

float 是单精度的浮点数遵循 IEEE 754二进制浮点数算术标准取值范围是无限的默认值为 0.0f。float 不适合用于精确的数值比如说货币。代码示例

float f1 = 234.5f;

为了和 double 作区分float 型变量在声明的时候末尾要带上小写的“f”。不需要使用大写的“F”是因为小写的“f”很容易辨别。


🍃07、double

double 是双精度的浮点数遵循 IEEE 754二进制浮点数算术标准取值范围也是无限的默认值为 0.0。double 同样不适合用于精确的数值比如说货币。代码示例

double d1 = 12.3

那精确的数值用什么表示呢最好使用 BigDecimal它可以表示一个任意大小且精度完全准确的浮点数。针对货币类型的数值也可以先乘以 100 转成整型进行处理。

Tips单精度是这样的格式1 位符号8 位指数23 位小数有效位数为 7 位。

双精度是这样的格式1 位符号11 位指数52 为小数有效位数为 16 位。

取值范围取决于指数位计算精度取决于小数位尾数。小数位越多则能表示的数越大那么计算精度则越高。

一个数由若干位数字组成其中影响测量精度的数字称作有效数字也称有效数位。有效数字指科学计算中用以表示一个浮点数精度的那些数字。一般地指一个用小数形式表示的浮点数中从第一个非零的数字算起的所有数字。如 1.24 和 0.00124 的有效数字都有 3 位。

🍃08、char

char 可以表示一个 16 位的 Unicode 字符其值范围在 '\u0000'0和 '\uffff'65,535包含之间。代码示例

char letterA = 'A'; 

“char占两个字节主要是因为 Java 使用的是 Unicode 字符集而不是 ASCII 字符集。字符集也可以叫编码编码不同实际占用的字节就会不同。”

🌴类型转换

关于类型转换主要分为强制类型转换和自动类型转换还有一些方法可以转换后面再具体说

🍃01、强制类型转换

强转语法就是在需要转换的类型前面加上

(type)variableName

代码示例如下

public class SimpleTesting {
    public static void main(String[] args) {
        int value_int = 65;
        char value_char  = (char) value_int;
        System.out.println(value_char);
    }
} 
A    //65在 ASCII 码中对应的字符是A

🍃02、自动类型转换

规则从小到大 低字节向高字节自动提升

顺序

byte(1字节) – > short(2字节)-- > int(4字节) – > long(8字节) --> float(4字节) – > double(8字节)

char (2字节)-- > int(4字节) – > long(8字节) --> float(4字节) – > double(8字节)

画图分析

🍃03、什么时候会发生类型转换       

答 赋值 | 运算时 两边数据类型不一致时就会发生类型转换


🌲引用数据类型

基本数据类型在作为成员变量和静态变量的时候有默认值引用数据类型也有的。

String 是最典型的引用数据类型所以我们就拿 String 类举例看下面这段代码

public class LocalRef {
    private String a;
    static String b;

    public static void main(String[] args) {
        LocalRef lv = new LocalRef();
        System.out.println(lv.a);
        System.out.println(b);
    }
}

输出结果如下所示

null
null

null 在 编程语言 中是一个很神奇的存在在你以后的程序生涯中见它的次数不会少尤其是伴随着令人烦恼的“空指针异常open in new window”也就是所谓的 NullPointerException

也就是说引用数据类型的默认值为 null包括数组和接口。

你可能会问为什么数组和接口也是引用数据类型啊

先来看数组

public class ArrayDemo {
    public static void main(String[] args) {
        int [] arrays = {1,2,3};
        System.out.println(arrays);
    }
}

arrays 是一个 int 类型的数组对吧打印结果如下所示

[I@2d209079

[I 表示数组是 int 类型的@ 后面是十六进制的 hashCode——这样的打印结果太“人性化”了一般人表示看不懂为什么会这样显示呢查看一下 java.lang.Object 类的 toString() 方法就明白了。

数组虽然没有显式定义成一个类但它的确是一个对象继承了祖先类 Object 的所有方法。那为什么数组不单独定义一个类来表示呢就像字符串 String 类那样呢

一个合理的解释是 Java 将其隐藏了。假如真的存在一个 Array.java我们也可以假想它真实的样子它必须要定义一个容器来存放数组的元素就像 String 类那样。

public final class String
    implements java.io.Serializable, Comparable<String>, CharSequence {
    /** The value is used for character storage. */
    private final char value[];
}

数组内部定义数组没必要的

再来看接口

public class IntefaceDemo {
    public static void main(String[] args) {
        List<String> list = new ArrayList<>();
        System.out.println(list);
    }
}

List 是一个非常典型的接口

public interface List<E> extends Collection<E> {}

而 ArrayList 是 List 接口的一个实现

public class ArrayList<E> extends AbstractList<E>
        implements List<E>, RandomAccess, Cloneable, java.io.Serializable
{}

对于接口类型的引用变量来说你没法直接 new 一个

只能 new 一个实现它的类的对象——那自然接口也是引用数据类型了。

来看一下基本数据类型和引用数据类型之间最大的差别。

基本数据类型

  • 1、变量名指向具体的数值。
  • 2、基本数据类型存储在栈上。

引用数据类型

  • 1、变量名指向的是存储对象的内存地址在栈上。
  • 2、内存地址指向的对象存储在堆上。

堆是堆heap栈是栈stack如果看到“堆栈”的话请不要怀疑自己那是翻译的错堆栈也是栈。

堆是在程序运行时在内存中申请的空间可理解为动态的过程程序员自己new出来的切记不是在编译时因此Java 中的对象就放在这里这样做的好处就是

当需要一个对象时只需要通过 new 关键字写一行代码即可当执行这行代码时会自动在内存的“堆”区分配空间——这样就很灵活。

栈能够和处理器CPU也就是脑子直接关联因此访问速度更快。既然访问速度快要好好利用啊Java 就把对象的引用放在栈里。为什么呢因为引用的使用频率高吗

不是的因为 Java 在编译程序时必须明确的知道存储在栈里的东西的生命周期否则就没法释放旧的内存来开辟新的内存空间存放引用——空间就那么大。


🌲Java 运算符

🍐01、算数运算符

算术运算符除了最常见的加减乘除还有一个取余的运算符用于得到除法运算后的余数。

        int a = 10;
        int b = 5;

        System.out.println(a + b);//15
        System.out.println(a - b);//5
        System.out.println(a * b);//50
        System.out.println(a / b);//2
        System.out.println(a % b);//0

        b = 3;
        System.out.println(a + b);//13
        System.out.println(a - b);//7
        System.out.println(a * b);//30
        System.out.println(a / b);//3
        System.out.println(a % b);//1

对于初学者来说加法+、减法-、乘法*很好理解但除法/和取余%会有一点点疑惑。在以往的认知里10/3 是除不尽的结果应该是 3.333333...而不应该是 3。相应的余数也不应该是 1。这是为什么呢

因为数字在程序中可以分为两种一种是整型一种是浮点型整型和整型的运算结果就是整型不会出现浮点型。否则就会出现浮点型。

🍐02、关系运算符

关系运算符用来比较两个操作数返回结果为 true 或者 false。

🍐 03、位运算符

public class BitOperator {
    public static void main(String[] args) {
        int a = 60, b = 13;
        System.out.println("a 的二进制" + Integer.toBinaryString(a)); // 111100
        System.out.println("b 的二进制" + Integer.toBinaryString(b)); // 1101

        int c = a & b;
        System.out.println("a & b" + c + "二进制是" + Integer.toBinaryString(c));

        c = a | b;
        System.out.println("a | b" + c + "二进制是" + Integer.toBinaryString(c));

        c = a ^ b;
        System.out.println("a ^ b" + c + "二进制是" + Integer.toBinaryString(c));

        c = ~a;
        System.out.println("~a" + c + "二进制是" + Integer.toBinaryString(c));

        c = a << 2;
        System.out.println("a << 2" + c + "二进制是" + Integer.toBinaryString(c));

        c = a >> 2;
        System.out.println("a >> 2" + c + "二进制是" + Integer.toBinaryString(c));

        c = a >>> 2;
        System.out.println("a >>> 2" + c + "二进制是" + Integer.toBinaryString(c));
    }
}

1按位左移运算符

public class LeftShiftOperator {
    public static void main(String[] args) {
        System.out.println(10<<2);//10*2^2=10*4=40  
        System.out.println(10<<3);//10*2^3=10*8=80  
        System.out.println(20<<2);//20*2^2=20*4=80  
        System.out.println(15<<4);//15*2^4=15*16=240  
    }
}

10<<2 等于 10 乘以 2 的 2 次方10<<3 等于 10 乘以 2 的 3 次方。

2按位右移运算符

public class RightShiftOperator {
    public static void main(String[] args) {
        System.out.println(10>>2);//10/2^2=10/4=2
        System.out.println(20>>2);//20/2^2=20/4=5
        System.out.println(20>>3);//20/2^3=20/8=2
    }
}

10>>2 等于 10 除以 2 的 2 次方20>>2 等于 20 除以 2 的 2 次方。

🍐04、逻辑运算符

逻辑与运算符&&多个条件中只要有一个为 false 结果就为 false。

逻辑或运算符||多个条件只要有一个为 true 结果就为 true。

public class LogicalOperator {
    public static void main(String[] args) {
        int a=10;
        int b=5;
        int c=20;
        System.out.println(a<b&&a<c);//false && true = false

        System.out.println(a>b||a<c);//true || true = true
    }
}

逻辑非运算符!用来反转条件的结果如果条件为 true则逻辑非运算符将得到 false。

单逻辑与运算符&很少用因为不管第一个条件为 true 还是 false依然会检查第二个。

单逻辑或运算符|也会检查第二个条件。

也就是说& 和 | 性能不如 && 和 ||但用法一样

public class LogicalOperator1 {
    public static void main(String[] args) {
        int a=10;
        int b=5;
        int c=20;
        System.out.println(a<b&a<c);//false & true = false

        System.out.println(a>b|a<c);//true | true = true  
    }
}

🍐05、赋值运算符

赋值操作符恐怕是 Java 中使用最频繁的操作符了它就是把操作符右侧的值赋值给左侧的变量。来看示例

public class AssignmentOperator {
    public static void main(String[] args) {
        int a=10;
        int b=20;
        a+=4;//a=a+4 (a=10+4)  
        b-=4;//b=b-4 (b=20-4)  
        System.out.println(a);
        System.out.println(b);
    }
}

不过在进行数值的赋值时需要小点心比如说下面这种情况

编译器之所以提示错误是因为 = 右侧的算术表达式默认为 int 类型左侧是 short 类型的时候需要进行强转。

public class AssignmentOperator1 {
    public static void main(String[] args) {
        short a = 10;
        short b = 10;
//a+=b;//a=a+b internally so fine
        a = (short)(a + b);
        System.out.println(a);
    }
}

除此之外还会有边界问题比如说两个非常大的 int 相乘结果可能就超出了 int 的范围

public class BigIntMulti {
    public static void main(String[] args) {
        int a = Integer.MAX_VALUE;
        int b = 10000;
        int c = a * b;
        System.out.println(c); // -10000
    }
}

程序输出的结果为 -10000这个答案很明显不是我们想要的结果虽然可以通过右侧表达式强转 long 的方法解决

public class BigIntMulti {
    public static void main(String[] args) {
        int a = Integer.MAX_VALUE;
        int b = 10000;
        long c = (long)a * b;
        System.out.println(c); // 21474836470000
    }
}

但尽量不要这样做结果非常大的时候尽量提前使用相应的类型进行赋值。

long a = Integer.MAX_VALUE - 1;
long b = 10000;
long c = a * b;
System.out.println(c); // 21474836460000

🍐06、三元运算符

三元运算符用于替代 if-else可以使用一行代码完成条件判断的要求。来看示例

public class TernaryOperator {
    public static void main(String[] args) {
        int a=2;
        int b=5;
        int min=(a<b)?a:b;
        System.out.println(min);
    }
}

如果 ? 前面的条件为 true则结果为 : 前的值否则为 : 后的值。这个可以用 if 语句来替代。


流程控制语句

可以直接去看我之前写的C++的没什么区别

阿里云国内75折 回扣 微信号:monov8
阿里云国际,腾讯云国际,低至75折。AWS 93折 免费开户实名账号 代冲值 优惠多多 微信号:monov8 飞机:@monov6
标签: Java