精华内容
下载资源
问答
  • Java每日一题【1】JAVA中的几种基本数据类型是什么,各自占用多少字节?
    千次阅读
    2020-09-11 22:20:16

    整理一下脑子里的知识,也算温故知新吧。

    一、Java四大数据类型分类

    1、整型

    byte 、short 、int 、long

    2、浮点型

    float 、 double

    3、字符型

    char

    4、布尔型

    boolean


     

    二、八种基本数据类型

     


     

    三、数据类型详细介绍

    整型(byte、short、int、long)

     

    虽然byte、short、int、long 数据类型都是表示整数的,但是它们的取值范围可不一样。

    byte 的取值范围:-128~127(-2的7次方到2的7次方-1)

    short 的取值范围:-32768~32767(-2的15次方到2的15次方-1)

    int 的取值范围:-2147483648~2147483647(-2的31次方到2的31次方-1)

    long 的取值范围:-9223372036854774808~9223372036854774807(-2的63次方到2的63次方-1)

    由上可以看出 byte、short 的取值范围比较小,而long的取值范围时最大的,所以占用的空间也是最多的。int 取值范围基本上可以满足我们的日常计算需求了,所以 int 也是我们使用的最多的一个整型类型。

     

    浮点型(float、double)

    float 和 double 都是表示浮点型的数据类型,它们之间的区别在于精确度的不同。

    float(单精度浮点型)取值范围:3.402823e+38~1.401298e-45(e+38 表示乘以10的38次方,而e-45 表示乘以10的负45次方)

    double(双精度浮点型)取值范围:1.797693e+308~4.9000000e-324(同上)

    double 类型比float 类型存储范围更大,精度更高。

    通常的浮点型数据在不声明的情况下都是double型的,如果要表示一个数据时float 型的,可以在数据后面加上 "F" 。

    浮点型的数据是不能完全精确的,有时候在计算时可能出现小数点最后几位出现浮动,这时正常的。

    字符型(char)

     

    char 有以下的初始化方式:

    char ch = 'a'; // 可以是汉字,因为是Unicode编码

    char ch = 1010; // 可以是十进制数、八进制数、十六进制数等等。

    char ch = '\0'; // 可以用字符编码来初始化,如:'\0' 表示结束符,它的ascll码是0,这句话的意思和 ch = 0 是一个意思。

    Java是用unicode 来表示字符,“中” 这个中文字符的unicode 就是两个字节。

    String.getBytes(encoding) 方法获取的是指定编码的byte数组表示。

    通常gbk / gb2312 是两个字节,utf-8 是3个字节。

    如果不指定encoding 则获取系统默认encoding 。

     

    布尔型(boolean)

    boolean 没有什么好说的,它的取值就两个:true 、false 。


     

    四、基本类型之间的转换

    将一种类型的值赋值给另一种类型是很常见的。在Java中,boolean 类型与其他7中类型的数据都不能进行转换,这一点很明确。但对于其他7种数据类型,它们之间都可以进行转换,只是可能会存在精度损失或其他一些变化。

    转换分为自动转换和强制转换:

    自动转换(隐式):无需任何操作。

    强制转换(显式):需使用转换操作符(type)。

    将6种数据类型按下面顺序排列一下:

    double > float > long > int > short > byte

    如果从小转换到大,那么可以直接转换,而从大到小,或char 和其他6种数据类型转换,则必须使用强制转换。

    1、自动转换

    自动转换时发生扩宽(widening conversion)。因为较大的类型(如int)要保存较小的类型(如byte),内存总是足够的,不需要强制转换。如果将字面值保存到byte、short、char、long的时候,也会自动进行类型转换。注意区别,此时从int(没有带L的整型字面值为int)到byte/short/char也是自动完成的,虽然它们都比int小。在自动类型转化中,除了以下几种情况可能会导致精度损失以外,其他的转换都不能出现精度损失。

    》int--> float

    》long--> float

    》long--> double

    》float -->double without strictfp

    除了可能的精度损失外,自动转换不会出现任何运行时(run-time)异常。

    2、强制类型转换

    如果要把大的转成小的,或者在short与char之间进行转换,就必须强制转换,也被称作缩小转换(narrowing conversion),因为必须显式地使数值更小以适应目标类型。强制转换采用转换操作符()。严格地说,将byte转为char不属于narrowing conversion),因为从byte到char的过程其实是byte-->int-->char,所以widening和narrowing都有。强制转换除了可能的精度损失外,还可能使模(overall magnitude)发生变化。强制转换格式如下:

    (target-type) value;

    如果整数的值超出了byte所能表示的范围,结果将对byte类型的范围取余数。例如a=256超出了byte的[-128,127]的范围,所以将257除以byte的范围(256)取余数得到b=1;需要注意的是,当a=200时,此时除了256取余数应该为-56,而不是200。

    将浮点类型赋给整数类型的时候,会发生截尾(truncation)。也就是把小数的部分去掉,只留下整数部分。此时如果整数超出目标类型范围,一样将对目标类型的范围取余数。

    7种基本类型转换总结如下图:

     

     

    3、赋值及表达式中的类型转换

    3.1、字面值赋值

    在使用字面值对整数赋值的过程中,可以将int literal赋值给byte short char int,只要不超出范围。这个过程中的类型转换时自动完成的,但是如果你试图将long literal赋给byte,即使没有超出范围,也必须进行强制类型转换。例如 byte b = 10L;是错的,要进行强制转换。

    3.2、表达式中的自动类型提升

    除了赋值以外,表达式计算过程中也可能发生一些类型转换。在表达式中,类型提升规则如下:

    · 所有byte/short/char都被提升为int。

    · 如果有一个操作数为long,整个表达式提升为long。float和double情况也一样。


     

    拓展知识点:Java是面向对象语言,其概念为一切皆为对象,但基本数据类型算是个例外哦,基本数据类型大多是面向机器底层的类型,它是 “值” 而不是一个对象,它存放于“栈”中而不是存放于“堆”中,但Java一切皆为对象的概念不是说说而已,它为每一个基本数据类型都做了相应的包装类,我们日常使用中大多情况下都会使用着这些包装类:


    boolean Boolean
    char Character
    byte Byte
    short Short
    int Integer
    long Long
    float Float
    double Double
    String(字符串)
    包装类就是一个对象,它存放于“堆”中。

    更多相关内容
  • 二、JAVA语言基础

    千次阅读 2021-03-13 04:47:22
    1、 Java程序的基本结构JAVA是面向对象的程序设计语言,JAVA程序的基本组成单元是类,类又包含属性与方法两部分,每一个应用程序都必须包含一个main()方法,含有main()方法的类称为主类。一个Java应用程序是由若干...

    1、 Java程序的基本结构

    JAVA是面向对象的程序设计语言,JAVA程序的基本组成单元是类,类中又包含属性与方法两部分,每一个应用程序都必须包含一个main()方法,含有main()方法的类称为主类。一个Java应用程序是由若干个类组成的语句package Number为声明该类所在的包,package为包的关键字。

    2 、声明、包导入

    import 和 package 都是在对字节码文件进行操作,和源码没关系,因为源码是给人看的,字节码才是给机器运行的,对机器而言根本就不存在源码这种东西。

    import 是用来指定去哪里找字节码文件,package 是用来指定这个 java 文件编译后的字节码放到指定的目录下。

    包导入 import 关键字的作用是:

    当该字节码文件在执行过程中,需要用到了本包中没有的字节码文件时,就会主动在当前目录下去寻找 import 关键字指明的字节码文件,import关键字后面接的就是一个类字节码文件的全名。

    包声明 package 关键字有以下作用:

    从源码的角度来看,按照包名创建相应文件夹来管理 .java 源文件,体现了分包管理的机制,也为 java 程序的权限机制提供了必要条件。

    从字节码的角度看,一个类的完整名字(包名.类名)是把包名也包含进去了的。

    3、 声明成员变量和局部变量

    通常将类的属性称之为类的全局变量(成员变量),将方法中的属性称之为局部变量。全局变量声明在类体中,局部变量声明在方法体中。

    全局变量和局部变量都有各自的应用范围。

    4、 编写主方法

    main()方法是类体中的主方法。该方法从“{”号开始,至“}”号结束。

    public、static和void分别是main()方法的权限修饰符、静态修饰符和返回值修饰符,Java程序中的main()方法必须声明为public static void。

    String[] args是一个字符串类型的数组,它是main()方法的参数。main()方法是程序开始执行的位置。

    5、导入API类库

    在Java语言中可以通过import关键字导入相关的类。在JDK的API中(应用程序接口)提供了130多个包,如java.awt、java.io等。

    可以通过JDK的API文档来查看这些类,其中主要包括类的继承结构、类的应用、成员变量表、构造方法表等,并对每个变量的使用目的作了详细的描述,因此,API文档是程序开发人员不可或缺的工具。

    6、 基本数据类型

    1)计算机存储单元

    变量是内存中的小容器,用来存储数据。那么计算机内存是怎么存储数据的呢?

    无论是内存还是硬盘,计算机存储设备的最小信息单元叫“位(bit)”,我们又称之为“比特位”,通常用小写的字母b表示。

    而计算机最小的存储单元叫“字节(byte)”,通常用大写字母B表示,字节是由连续的8个位组成。

    除了字节外还有一些常用的存储单位,大家可能比较熟悉,我们一起来看看:

    1B(字节) = 8bit

    1KB = 1024B

    1MB = 1024KB

    1GB = 1024MB

    1TB = 1024GB

    bit  电脑记忆体中最小的单位,在二进位电脑系统中,每一bit 可以代表0 或 1 的数位讯号。

    Byte   一个Byte由8 bits 所组成,可代表一个字元(A~Z)、数字(0~9)、或符号(,.?!%&+-*/),是记忆体储存资料的基本单位,至於每个中文字则须要两Bytes。

    2)数据类型概述和分类

    A:为什么有数据类型

    Java语言是强类型语言,对于每一种数据都定义了明确的具体数据类型,在内存中分配了不同大小的内存空间

    B:Java中数据类型的分类

    基本数据类型

    引用数据类型

    Java语言提供了八种基本类型(4类8种)。

    4710561b28f5b6cdd7cadb0cc9a37695.png

    1ac63eda6309c29d9817e3101cbf1c21.png

    byte:默认值是 0;

    short:默认值是 0;

    int:默认值是 0 ;

    long:默认值是 0L;("L"理论上不分大小写,但是若写成"l"容易与数字"1"混淆,不容易分辩。所以最好大写。在对long型变量赋值时结尾必须加上“L”或者“l”,否则将不被认为是long型。)

    float:默认值是 0.0f;(浮点数不能用来表示精确的值,如货币;在对float型进行赋值的时候在结尾必须添加“F”或者“f”,如果不加,系统自动将其定义为double型变量.)

    double:默认值是 0.0d;

    (浮点数的默认类型为double类型;double类型同样不能表示精确的值,如货币;在给double型赋值时,可以使用后缀“D”或“d”明确表明这是一个double类型数据,但加不加并没有硬性规定,可以加也可以不加。)

    boolean:默认值是 false;

    char 字符型:

    char类型是一个单一的 16位(2个字节) Unicode 字符;最小值是 \u0000(即为0);最大值是 \uffff(即为65,535);

    char 数据类型可以储存任何字符;在定义字符型变量时,要用单引号括起来,例如‘s’表示一个字符,且单引号中只能有一个字符,多了就不是字符类型了,而是字符串类型,需要用双引号进行声明。

    对于数值类型的基本类型的取值范围,我们无需强制去记忆,因为它们的值都已经以常量的形式定义在对应的包装类中了。如下:

    System.out.println("基本类型:byte 二进制位数:" + Byte.SIZE);

    System.out.println("包装类:java.lang.Byte");

    System.out.println("最小值:Byte.MIN_VALUE=" + Byte.MIN_VALUE);

    System.out.println("最大值:Byte.MAX_VALUE=" + Byte.MAX_VALUE);

    引用类型

    在Java中,引用类型的变量非常类似于C/C++的指针。引用类型指向一个对象,指向对象的变量是引用变量。

    这些变量在声明时被指定为一个特定的类型,比如 Employee、Puppy 等。变量一旦声明后,类型就不能被改变了。

    对象、数组、字符串都是引用数据类型。

    所有引用类型的默认值都是null。

    注意:

    整数默认是int类型,定义long类型的数据时,要在数据后面加L。

    浮点数默认是double类型,定义float类型的数据时,要在数据后面F。

    3)Java语言支持一些特殊的转义字符序列

    符号

    字符含义

    \n

    换行 (0x0a)

    \r

    回车 (0x0d)

    \f

    换页符(0x0c)

    \b

    退格 (0x08)

    \0

    空字符 (0x20)

    \s

    字符串

    \t

    制表符

    \"

    双引号

    \'

    单引号

    \\

    反斜杠

    \ddd

    八进制字符 (ddd)

    \uxxxx

    16进制Unicode字符 (xxxx)

    4) 数据类型转换

    输出各种类型的数据

    上溢:当被赋值的变量的值太大而无法存储时,称为上溢。上溢不会警告或报错。

    下溢:当浮点数太小而不能存储时,称为下溢,Java 将其近似为0,也不会警告或报错。

    取值范围小的数据类型与取值范围大的数据类型进行运算,会先将小的数据类型提升为大的,再运算

    整型、实型(常量)、字符型数据可以混合运算。运算中,不同类型的数据先转化为同一类型,然后进行运算。

    转换从低级到高级。

    int + int 其结果为int型

    byte + bytebyte类型的变量在进行运算时,会自动提升为int型。

    byte + int将byte型隐式转换为int型,然后相加赋值给int型(结果必须为int型)

    对于short型,

    short + short的结果为int型;

    short + byte 的结果也为int型

    总结:

    在进行混合运算时,byte、short、char不会相互转换,都会自动提升为int类型,其他类型进行混合运算时小的数据类型提升为大的(字节数)。byte、short、char → int → long → float → double

    数据类型转换必须满足如下规则:

    1. 不能对boolean类型进行类型转换。

    2. 不能把对象类型转换成不相关类的对象。

    3. 在把容量大的类型转换为容量小的类型时必须使用强制类型转换。

    4. 转换过程中可能导致溢出或损失精度,例如:

    int i =128; byte b = (byte)i;

    因为 byte 类型是 8 位,最大值为127,所以当 int 强制转换为 byte 类型时,值 128 时候就会导致溢出。

    5. 浮点数到整数的转换是通过舍弃小数得到,而不是四舍五入,例如:

    (int)23.7 == 23;        (int)-45.89f == -45

    A.隐式数据类型转换(自动类型转换)

    /*+: 是一个运算符,做加法运算的。

    我们在做运算的时候,一般要求参与运算的数据类型必须一致。

    类型转换:

    隐式转换

    强制转换

    隐式转换

    数值型数据的转换:byte→short→int→long→float→double。

    字符型转换为整型:char→int。*/

    public classTypeCastDemo {public static voidmain(String[] args) {//直接输出了运算的结果

    System.out.println(3 + 4);//定义两个int类型的变量

    int a = 3;int b = 4;int c = a +b;

    System.out.println(c);//定义一个byte类型,定义一个int类型

    byte bb = 2;int cc = 5;

    System.out.println(bb+cc);//我能不能不直接输出,用一个变量接受呢?//用变量接受,这个变量应该有类型//可能损失精度//byte dd = bb + cc;

    int dd = bb +cc;

    System.out.println(dd);

    }

    }

    B.强制类型数据转换

    强制转换的格式: b = (byte)(a + b);

    强制转换的注意事项

    * 如果超出了被赋值的数据类型的取值范围得到的结果会与你期望的结果不同

    /*强制转换:

    目标类型 变量名 = (目标类型) (被转换的数据);

    不建议强制转换,因为会有精度的损失。*/

    public classTypeCastDemo2 {public static voidmain(String[] args) {int a = 3;byte b = 4;int c = a +b;//byte d = a + b;

    byte d = (byte) (a +b);

    }

    }

    7、代码注释和编码规范

    A.代码注释

    用于解释说明程序的文字

    类似于C/C++,Java也支持单行以及多行注释。注释中的字符将被Java编译器忽略。

    Java语言提供了3种添加注释的方法,分别为单行注释、多行注释和文档注释。

    B: Java中注释分类

    单行注释 格式: //注释文字

    多行注释 格式: /* 注释文字 */

    文档注释 格式:/** 注释文字 */

    C: 注释的作用

    解释说明程序,帮助我们调试错误

    C.编码规范

    良好的编码规范会给程序的开发与日后的维护提供很大方便。总结的编码规范如下:

    * 每条语句要单独占一行

    * 每条命令都要以分号结束

    * 声明变量时要分行声明

    * Java语句中多个空格看成一个

    * 不要使用技术性很高、难懂、易混淆判断的语句

    * 对于关键的方法要多加注释

    展开全文
  • Java中基本操作单元 - 类和对象

    千次阅读 多人点赞 2020-02-26 18:51:25
    说到类和对象,这都是两个比较抽象的词,如果用程序,那就更不知道是什么意思了。其实大家可以先不联系程序,我们对一大堆东西分类的时候自然是有一个标准的,符合某些特征的分到一类,符合另外一些特征的分到...

    写在前面:博主是一只经过实战开发历练后投身培训事业的“小山猪”,昵称取自动画片《狮子王》中的“彭彭”,总是以乐观、积极的心态对待周边的事物。本人的技术路线从Java全栈工程师一路奔向大数据开发、数据挖掘领域,如今终有小成,愿将昔日所获与大家交流一二,希望对学习路上的你有所助益。同时,博主也想通过此次尝试打造一个完善的技术图书馆,任何与文章技术点有关的异常、错误、注意事项均会在末尾列出,欢迎大家通过各种方式提供素材。

    • 对于文章中出现的任何错误请大家批评指出,一定及时修改。
    • 有任何想要讨论和学习的问题可联系我:zhuyc@vip.163.com。
    • 发布文章的风格因专栏而异,均自成体系,不足之处请大家指正。

    Java中的基本操作单元 - 类和对象

    本文关键字:类、属性、行为、实例化、对象

    一、概念浅析

    说到类和对象,这都是两个比较抽象的词,如果用在程序中,那就更不知道是什么意思了。其实大家可以先不联系程序,我们在对一大堆东西分类的时候自然是有一个标准的,符合某些特征的分到一类,符合另外一些特征的分到另外一类。在每个类别中,每一样东西都有相同的特征,但是又有所差别,每一样东西就好比一个一个的对象,是一个切切实实的东西,而分类的类别就好似是一个标准或者描述,会更抽象一些。

    1. 类的概念

    在编程中,我们通常会借助程序去实现很多应用系统,来满足日常生活中的需要,如网络购物、人力资源管理等等。如果使用面向对象来开发,首先需要做的就是明确这个应用系统当中有哪些角色,这些角色都能够使用哪些功能,每种角色都有哪些自己的特征。
    我们以一个教学管理系统为例,主要的功能就是进行排课,记录学生和教师的基本信息,记录和统计学生的学习成绩等。那这其中主要就涉及学生、教师、管理员三种角色,当有一批学生入学时,我们要将学生的信息录入系统,这就好像我们一直在填的各种表格,每个学生需要采集的信息都是固定的,不同的是信息的内容。
    在这里插入图片描述
    这就好比我们定义了一个学生类,我们想要收集的学生信息就是对这个类别的描述,学生有学号、有院系、有其他的基本信息,这也是学生的固有特征,于是我们可以用如下的代码描述:

    // 用于描述学生的类
    public class Student{
        String sno;// 学号
        String name;// 姓名
        String college;// 学院
        String major;// 专业
        ...
    }
    

    2. 什么是对象

    理解了程序中类的概念和表示方式后,对象就比较好理解了。简单来说对象就是按照类的标准创建出来的一个具体可以操作的东西,也就是一个个具体的学生。每个学生都具备相同的特征,但是可以有不同的姓名、学院、专业等自己的信息。在程序运行时的体现就是内存中开辟了对应的空间,想要创建一个新的对象使用如下的代码:

    public class Test{
        public static void main(String[] args){
            // 变量类型 变量名称 = new 类的构造器();
            Student student = new Student();
            // 大写的Student就是我们要使用的学生类型,名称必须完全一致
            // 小写的student就是由学生类创建出来的对象的名称
            // 也是我们操作对象时直接使用的名称
            // new是用来创建对象的关键字,需要调用相应的构造器
            // 有关于构造器的用法会在后续文章详细说明,初学可以记忆为:类名();
        }
    }
    

    3. 类和对象的关系

    从上面的例子中我们已经可以看到,类相当于是一个模板或是像工厂的图纸,对象则相当于按照这个标准和模具创造出来的个体,每一个对象都具备相同的特征。
    在程序中的体现就是,使用class关键字定义一个类结构,然后在这个结构中对整个类进行描述,都具备哪些属性,都可以产生行为,但是只有具体的对象可以具备具体的属性值和产生具体的行为(有关于静态的声明将在另外的文章中单独说明)。

    二、类

    我们应该如何描述和定义一个类呢?我们最开始写的HelloWorld不也是一个类嘛?为什么没这么多乱七八糟的概念?下面我们就来进一步解析。
    从客观世界的角度出发,比如小明上了大学,这就是一个具体的学生,他有学号、姓名、对应的学院、专业等等,这都是他个人的基本信息,除此之外,他还可以进行多种活动,比如选课、考试、修改自己的部分信息等等。
    在这里插入图片描述
    那么我们从程序的角度出发,应该如何定义一个类呢?这取决于我们的需要,对于一个教学管理系统来说,我们关心的只是和学生学习相关的信息,学生能够选课、考试等等。对于一个后勤管理系统来说,我们关心的则是学生的饭卡消费情况,出入宿舍的时间,学生能够充值、消费、刷卡等等。所以如何定义和描述一个类,取决于我们的应用系统需要,或者是题目的要求。

    1. 属性

    属性指的就是所描述的类当前的状态,也就是他自己的一些信息,直接在类下进行定义,和正常声明一个变量的格式相同,可以不指定初始值。

    2. 行为

    行为指的就是当前这个类所创建出的对象都能进行什么样的行为,在程序上的表现就是方法,可以被具体的对象来进行调用,在方法体中用代码实现具体的功能。

    // 用于描述学生的类
    public class Student{
        // 学生类的属性
        String sno;// 学号
        String name;// 姓名
        String college;// 学院
        String major;// 专业
        ...
    
        // 学生类的行为
        public void study(){
            // 去学习
            System.out.println("去上课");
        }
        public void exam(){
            // 去考试
            System.out.println("去考试");
        }
    }
    

    3. 可执行类

    在通常情况下,我们定义的一个类由四大部分构成:属性、行为、构造器以及其他继承Object的方法。也就是说都不存在可以直接执行的main方法,而只是为了定义一个我们想要使用的类,那么怎么样才能调用到,把我们的类用起来呢?就是通过那些具备main方法的类,如最初我们使用的HelloWorld,这就是一个最简形式的可执行类。

    public class HelloWorld{
        public static void main(String[] args){
            System.out.println("Hello World!");
        }
    }
    

    当然,我们也可以直接在类中添加main方法来测试运行,但是一般不会这样做,因为会有一些权限的问题不能够测试完整,通常的办法是新建一个单独的测试类,来进行调用测试。

    // 调用时需要将两个类放在同一目录下(同一包中)
    public class Test{
        public static void main(String[] args){
            // 创建一个学生对象
            Student student = new Student();
            // 为对象的属性赋值
            student.sno = "1130050152";
            student.name = "小明";
            student.college = "数学科学学院";
            student.major = "信息与计算科学";
            // 显示对象的属性值
            System.out.println("该学生的名字是:" + student.name);
            // 通过对象调用方法,发生行为
            student.study();
            student.exam();
        }
    }
    

    三、对象

    通过上面我们已经知道对象的概念,以及如何使用创建和使用一个对象。接下来我们再来明确一下类和对象,对象和对象之间的关系。

    1. 对象是类的实例

    创建对象的过程也可以被称之为实例化,对象也可以被叫做类的实例。这个概念也很好理解,在类中只是定义了一系列的描述信息,真正去执行需要靠具体的对象,以一个类为基准,可以创建出很多对象。

    2. 对象和对象之间的关系

    对象与对象之间存在共同点,除了使用静态声明的属性外,是不会互相影响的,这是一个很重要的特点。当我们使用不同的对象去调用方法和输出属性信息时,虽然类当中的结构完全一致,但是由于对象所处的状态(属性值)可能不同,那么方法执行的结果也会不同。

    // 用于描述学生的类
    public class Student{
        // 学生类的属性
        String sno;// 学号
        String name;// 姓名
        double balance;// 余额
        ...
    
        // 学生类的行为
        public void recharge(double money){
            // 对学生卡充值
            balance += money;
            System.out.println("当前余额为" + balance);
        }
        public void getBalance(){
            // 显示卡内余额
            System.out.println("当前余额为" + balance);
        }
    }
    
    // 测试类:将两个类放在同一目录下(同一包中)
    public class Test{
        public static void main(String[] args){
            // 创建第一个学生对象
            Student student1 = new Student();
            // 为对象的属性赋值
            student1.balance = 23.70;
            // 调用方法
            student1.getBalance();
            student1.recharge(100.0);
            // 创建第二个学生对象
            Student student2 = new Student();
            // 为对象的属性赋值
            student2.balance = 15.60;
            // 调用方法
            student2.getBalance();
            student2.recharge(50.0);
        }
    }
    

    程序执行完毕后可以再次输出查看两个对象的属性值,不会互相影响。

    扫描下方二维码,加入官方粉丝微信群,可以与我直接交流,还有更多福利哦~

    在这里插入图片描述

    展开全文
  • 如何写Java单元测试

    千次阅读 2021-01-19 10:23:06
     我们编写大型程序的时候,需要写成千上万个方法或函数,这些函数的功能可能很强大,但我们程序只用到该函数的一小部分功能,并且经过调试可以确定,这一小部分功能是正确的。但是,我们同时应该确保每一个...

    本文引自https://www.cnblogs.com/ysw-go/p/5447056.html

    什么是单元测试
      我们在编写大型程序的时候,需要写成千上万个方法或函数,这些函数的功能可能很强大,但我们在程序中只用到该函数的一小部分功能,并且经过调试可以确定,这一小部分功能是正确的。但是,我们同时应该确保每一个函数都完全正确,因为如果我们今后如果对程序进行扩展,用到了某个函数的其他功能,而这个功能有bug的话,那绝对是一件非常郁闷的事情。所以说,每编写完一个函数之后,都应该对这个函数的方方面面进行测试,这样的测试我们称之为单元测试。传统的编程方式,进行单元测试是一件很麻烦的事情,你要重新写另外一个程序,在该程序中调用你需要测试的方法,并且仔细观察运行结果,看看是否有错。这样的话太过于麻烦了,本文简要介绍一下在Eclipse中使用JUnit4进行单元测试的方法。用更加通俗的话来描述单元测试就是:写了个类,要给别人用,会不会有bug?怎么办?测试一下。用main方法测试好不好?这种方法我们经常用,就是写一个方法实现一些功能,把方法的调用方式放在main函数中。这样的测试方式一个是使得main函数太过于混乱,再者测试过程需要人的仔细观察来辨别每个函数的功能实现,哪一个函数出错了,哪一个函数没有输出之类的问题层出不穷,单元测试就是来解决这些问题的。下面我会就单元测试的每一步给出详细的图解和描述。

    第一部分

    我们先创建一个Java Project,名字就叫做JUnit4,然后创建两个包com.itcast.junit4和com.itcast.junit4.test,如下图所示
    在这里插入图片描述
    其中com.itcast.junit4用于我们自己写的类和方法的存放,com.itcast.junit4.test用于我们完成单元测试

    在com.itcast.junit4包中创建一个类叫做T(名字可以是任意的,这里是为了方便),在类中添加两个方法add和divide实现两个数的加法和除法运算

    package com.itcast.junit4;
       
      public class T {
       
          public int add(int x,int y){
              return x+y;
          }
          public int divide(int x,int y){
              return x/y;
         }
         public static void main(String[] args) {
             int z=new T().add(3, 5);
             System.out.println(z);
         }
      
     } 
    

    我们传统测试的方法通常都是按上面的方式去看add函数是否可以实现我们想要的功能,把方法的调用放在main函数中。下面我们看一下单元测试到底是什么东西:
    在com.itcast.junit4.test包中创建一个类,叫做TTest(单元测试命名规范:a) 类放在test包中;b) 类名用XXXTest结尾;c) 方法用testMethod命名;)
    在这里插入图片描述
    【步骤提示】com.itcast.junit4.test包–>右键–>New–Junit Test Case,然后选择New Junit 4 test,那个Junit 3已经过时了。下面的一行Class under test,单击右侧的Browser,在弹出的输入框中输入我们想要测试的类名T,选中单击next出现了一个界面要我们选择需要测试的方法,我们这里选择add方法和divide;
    在这里插入图片描述
    在这里插入图片描述
    接着出现了下面的界面:
    在这里插入图片描述
    这一步提示我们是否将我们需要的JUnit 4的相关包加入到我们项目的ClassPath路径下,点击OK就行,因为Eclipse中包含JUnit的jar包,我们暂且先用Eclipse自带的Junit4去测试,后面后将如何用我们自己下载的JUnit4 JAR包。

    做完上面的步骤会创建一个这样的测试类

    import static org.junit.Assert.*;
       
      import org.junit.Test;
       
      public class TTest {
       
          @Test
          public void testAdd() {
              fail("Not yet implemented");
         }
      
         @Test
         public void testDivide() {
             fail("Not yet implemented");
         }
      
     } 
    

    上面的org.junit.Assert.*;就是静态导入的我们实现单元测试要用到的一些方法;【注意】这是静态引入,可以把方法直接引入,org.junit.Assert是一个类,不是一个包,当然这些方法肯定都是静态方法了。出现的代码都是Assert类中的一些方法,"@Test”表明下面这个方法是一个测试方法,我们先删除自动生成的fail()函数的代码。添加以下代码:

    public class TTest {
      
         @Test
         public void testAdd() {
             int z=new T().add(2, 4);
             //判断z==6,以往的assert
             assertEquals(6, z);
         }
      
        @Test
        public void testDivide() {
            //测试T类中的divide方法
            int z=new T().divide(8, 2);
            System.out.println(z);
        }
     
    }
    

    我们现在开始进行测试:要测试的方法–>右键–>Run As–>JUnit Test
    在这里插入图片描述
    如果你想两个方法一块测试,则Run As–>选择Run Configurations:按图中选择相应的选项,然后点击Run
    在这里插入图片描述
    点击run会出现下面的结果:
    在这里插入图片描述
    绿条显示两个方法的功能没有错误,有这样的调试准则:keep the bar green,to keep the code clean,绿色代表测试成功,其中Error:程序出错 Failures:测试失败

    Error:是程序有问题,比如我们在testAdd方法中加上这一句:int a=8/0;再次测试这个方法则会出现一个Error

    public void testAdd() {
            int z=new T().add(2, 4);
            //判断z==6,以往的assert
            assertEquals(6, z);
            int a=8/0;
    }
    

    在这里插入图片描述
    可以看到最下方提示我们,我们写的方法中出现了除数为0的情况

    Failures:测试失败,比如我们在方法改成下面的形式:

    public void testAdd() {
            int z=new T().add(2, 4);
            //判断z==6,以往的assert
            assertEquals(6, z);
            assertTrue(z<3);
    //        int a=8/0;
    }
    

    再次测试一下我们的方法:则会出现调试失败的情况
    在这里插入图片描述

    第二部分

    通过上面的学习我们已经了解基本的单元测试的步骤,我们查看一下JUnit API可以看到org.junit.Assert类有很多类似于assertEquals(6, z);assertTrue(z<3);之类的方法的使用;
    在这里插入图片描述
    我们可以看到有很多方法都是以重载的形式出现的,比如我们前面的例子,在testAdd()方法中添加assertTrue(“z too small”,z>10);前面的字符串用于在我们测试失败的情况下给我们提示:因为8<10,所以会在测试失败的情况下给我们提示"z too small";

    重磅出击:assertThat

    assertThat(来自hamcrest包,所以我们需要下载hamcrest这个包,这里共享给大家,里面有很多我们平时都可以用到的JAR包和文件,地址:链接:http://pan.baidu.com/s/1sl02DOD 密码:ci5m): assertThat(actual, matcher);的出现可以替代其他所有的assert。放弃旧的断言,使用hamcrest断言。其中actual参数是实际的值,matcher可以是一个匹配器。在以后的项目开发中我们就可以使用assertThat代替前面出现的类如assertEquals(6, z); assertTrue(z<3);方法。

    首先第一步,我们想使用assertThat,需要添加两个jar包hamcrest-core-1.2和hamcrest-library-1.2,这两个包都在我的共享里了,想在把这两个包添加进我们的Java Project中JUnit4 Test–>右键–>Build Path–>Add External Archives,将这两个Jar加进去
    在这里插入图片描述
    添加以后:我们就可以使用assertThat了
    在这里插入图片描述
    我们把testAdd()方法改成下面的形式:

        @Test
        public void testAdd() {
            int z=new T().add(2, 4);
            assertThat(z, is(8));
            //判断z==6,以往的assert
    //        assertEquals(6, z);
    //        assertTrue(z<3);
    //        int a=8/0;
        }
    

    代码中的is()方法是在import static org.hamcrest.Matchers(这个类在我们加进来的hamcrest-core-1.2.jar内)类的一个方法我们需要将其静态引入,所以在最上面要加上下面这一句,应该就可以了;

    import static org.hamcrest.Matchers.*;
    

    但是,测试又出现了这样的错误:
    在这里插入图片描述
    我们可以看到Failure Trace第一行什么ClassLoader的错误,这是因为我们在这里用了两种包,一个是hamcrest包,一个是JUnit4的包,这两个包它们的ClassLoader用的不是一个(不清楚啥是ClassLoader,不要紧,先学会怎么解决,以后再研究)。解决方法很简单:在我们的JUnit4项目中–>右键JUnit->Build Path–>Remove from Build Path即可,如图所示:
    在这里插入图片描述
    然后我们自己将JUnit包引入进来(Junit也在我的分享文件中)

    JUnit4 Test–>右键–>Build Path–>Add External Archives,选择我们JUnit包中的junit-4.10,如下图所示:
    在这里插入图片描述
    ok!测试成功!

    assert的使用是测试代码更加自然(诸如这样的理解:z is 8),自己可以体会一下,下面给出一些实例,大家可以自己动手试一下

    示例
    a)assertThat( n, allOf( greaterThan(1), lessThan(15) ) );
    assertThat( n, anyOf( greaterThan(16), lessThan(8) ) );
    assertThat( n, anything() );
    assertThat( str, is( "bjsxt" ) );
    assertThat( str, not( "bjxxt" ) );
     
    b)assertThat( str, containsString( "bjsxt" ) );
    assertThat( str, endsWith("bjsxt" ) );
    assertThat( str, startsWith( "bjsxt" ) );
    assertThat( n, equalTo( nExpected ) );
    assertThat( str, equalToIgnoringCase( "bjsxt" ) );
    assertThat( str, equalToIgnoringWhiteSpace( "bjsxt" ) );
     
    c)assertThat( d, closeTo( 3.0, 0.3 ) );
    assertThat( d, greaterThan(3.0) );
    assertThat( d, lessThan (10.0) );
    assertThat( d, greaterThanOrEqualTo (5.0) );
    assertThat( d, lessThanOrEqualTo (16.0) );
     
    d)assertThat( map, hasEntry( "bjsxt", "bjsxt" ) );
    assertThat( iterable, hasItem ( "bjsxt" ) );
    assertThat( map, hasKey ( "bjsxt" ) );
    assertThat( map, hasValue ( "bjsxt" ) );
    

    第三部分 JUnit4 Annotation

    几种常见的注释形式:

    @Test: 测试方法
     a) (expected=XXException.class)
      
     b) (timeout=xxx)
      
     @Ignore: 被忽略的测试方法
     @Before: 每一个测试方法之前运行
     @After: 每一个测试方法之后运行
     @BeforeClass: 所有测试开始之前运行
    @AfterClass: 所有测试结束之后运行
    

    我们分别进行解释

    1)@Test,前面已经说明了,@Test注解表明下面的方法是一个测试方法,a), b)两种形式,比如@Test(expected=java.lang.ArithmeticException.class,timeout=100)a是在测试出现异常的情况下告知我们出现的异常信息,类似与try-catch中的e.printstacktrace() 方法,比较简单。b中的timeout=100,运行时间限制在100ms以内(通常在测试代码运行效率时这样设置)

    2)@ignore: 被忽略的测试方法(就是测试的时候跳过ignor标记的模块或方法)
    有时候某些方法还不具备测试的条件,暂时还不能测试或者某些方法已经不需要再做测试了,这就可以进行忽略的操作了。
    有时方法的测试条件还没满足,整个项目还差一个模块,则可以采用该方法假定测试条件成立。

    3)@after和@before

    我们把代码改成这个样子:为方便起见先把那个divide方法删掉

    public class TTest {
        @Before
        public void before() {
            System.out.println("befor");
        }
     
        @Test
        public void testAdd() {
            int z = new T().add(2, 4);
            assertThat(z, is(8));
            // 判断z==6,以往的assert
            // assertEquals(6, z);
            // assertTrue(z<3);
            // int a=8/0;
        }
     
        @After
        public void after() {
            System.out.println("after");
        }
     
    }
    

    当然需要在上面需要添加这两句:

    import org.junit.After;
    import org.junit.Before;
    

    测试一下我们的testAdd()方法,控制台输出:

    befor
    after
    

    说明@Before在每一个测试方法(@Test方法)之前运行 @After:在每一个测试方法之后运行。它们两个的应用场合: 有些方法需要执行的时候需要一些先决条件,比如打开某文件、获取资源,搭建环境,执行完之后需要关闭文件、释放资源、卸载环境这就需要before和after操作。

    4)@BeforeClass;@AfterClass,它们两个都是静态的方法。我们继续改写代码:

    public class TTest {
        @BeforeClass
        public static void beforeClass(){
            System.out.println("before class..");
        }
        @Before
        public void before() {
            System.out.println("befor");
        }
     
        @Test
        public void testAdd() {
            int z = new T().add(2, 4);
            assertThat(z, is(6));
            // 判断z==6,以往的assert
            // assertEquals(6, z);
            // assertTrue(z<3);
            // int a=8/0;
        }
     
        @After
        public void after() {
            System.out.println("after");
        }
        @AfterClass
        public static void afterClass(){
            System.out.println("after class..");
        }
     
    }
    

    当然也要加上:

    import org.junit.BeforeClass;
    import org.junit.AfterClass;
    

    输出结果:

    before class..
    befor
    after
    after class..
    

    这就说明了@BeforeClass 所有测试开始之前运行;@AfterClass: 所有测试结束之后运行【一定要注意】这两个方法都是静态方法,想想也应该明白类一加载就执行这两个方法,此时还没有创建任何对象,能执行的肯定就是静态方法了。

    总结:

    用了一天的时间学习了一下JUnit单元测试,其实还有很多东西没有看到,但对于单元测试的步骤和套路也算了解了一些,写在这里也方便自己以后的查阅和复习,待以后用到更深入的时候再更新一些单元测试在Spring/Mock中的应用,有错误的地方欢迎大家指出,再次谢谢大家的阅读!

    展开全文
  • java如何使用JUnit进行单元测试

    千次阅读 2021-02-12 22:18:59
    注:所有内容都是eclipse上实现,关于eclipse的安装和jdk的安装配置,请看:http://www.cnblogs.com/fench/p/5914827.html单元测试是什么?百度百科的解释是这样的:单元测试(模块测试)是开发者编写的一小段代码,...
  • 深入理解Java中的IO

    千次阅读 2021-02-12 22:56:33
    深入理解Java中的IO转载自:http://blog.csdn.net/qq_25184739/article/details/51205186本文的目录视图如下:Java IO概要a.Java IO常用的类b.Java流类的类结构图1.流的概念和作用2.Java IO所采用的模型 :3.IO流的...
  • java中定义类的关键字是什么

    千次阅读 2021-02-12 22:57:02
    类是 Java 的一种重要的引用数据类型,也是组成 Java 程序的基本要素,因为所有的 Java 程序都是基于类的。 Java 定义一个类,需要使用 class 关键字、一个自定义的类名和一对表示程序体的大括号。完整语法...
  • Java基础知识面试题(2020最新版)

    万次阅读 多人点赞 2020-02-19 12:11:27
    文章目录Java概述何为编程什么Javajdk1.5之后的三大版本JVM、JRE和JDK的关系什么是跨平台性?原理是什么Java语言有哪些特点什么是字节码?采用字节码的最大好处是什么什么Java程序的主类?应用程序和小程序的...
  • Java基本类型

    万次阅读 2021-12-17 21:25:42
    文章目录前言Java 虚拟机的 boolean 类型Java基本类型 前言 如果你了解面向对象语言...Java 这么做的原因主要是工程上的考虑,因为使用基本类型能够执行效率以及内存使用两方面提升软件性能。 今天,我们就来了
  • Java中八大基本数据类型详解

    万次阅读 多人点赞 2020-12-04 11:06:42
    自从Java发布以来,基本数据类型就是Java语言的一部分,分别是 byte, short, int, long, char, float, double, boolean .当然围绕着这些基本数据类型衍生出来了很多面试题,但是说实话,工作中基本用不到
  • Java中Calendar基本使用

    千次阅读 2021-09-20 14:55:52
    Java中Calendar基本使用 Calendar的常用日历字段 日历字段 Value YEAR 当前年份 MONTH 当前月份( 注:初始值是从0开始,所以得到的比实际月份小1月) DATE 一个月中的某天 WEEK_OF_YEAR 当前年中的第...
  • Java语言基本元素

    千次阅读 2020-11-27 11:19:18
    Java语言基本元素 1.标识符 1.1标识符概念 程序员对程序的元素加以命名时使用的命名记号称为标识符(identifier) 标识符包括:类名、变量名、常量名、方法名 1.2Java标识符命名规则 标识符的首字母必须是以下字符...
  • 教你如何更好的编写JAVA单元测试

    千次阅读 2021-05-18 22:53:56
    如何更好的编写JAVA单元测试 如各位希望转载或引用,请注明出处,尊重原创,谢谢。如有疑问或错误,欢迎邮件沟通。 gitHub地址:https://github.com/thinkingfioa 邮箱地址:thinking_fioa@163.com 博客地址: ...
  • 在Java中经常看到这样的字眼 1.@Override 2.@Deprecated 3.@SuppressWarnings  4.@SafeVarargs 5.@FunctionalInterface 很多小伙伴不知道什么意思,其实这是一种注解,注意是注解 ,不是“ // ”注释哦。 1....
  • 根据技术水平不同,Java程序员可以分为初级、中级、高级、资深等。不同级别的Java程序员,企业的要求也是有区别。下面播妞整理了初级Java程序员和中级Java程序员的应聘要求,供大家参考...
  • JAVA中什么是事物

    千次阅读 2019-04-20 11:39:12
    说起来事物,就跟数据库操作...事务的原子性:表示事务执行过程的任何失败都将导致事务所做的任何修改失效。 事务的一致性:表示当事务执行失败时,所有被该事务影响的数据都应该恢复到事务执行前的状态。 事务...
  • java中基本类型占用字节数

    千次阅读 2020-12-30 06:26:08
    在Java中一共有8种基本数据类型,其中有4种整型,2种浮点类型,1种用于表示Unicode编码的字符单元的字符类型和1种用于表示真值的boolean类型。(一个字节等于8个bit)1.整型类型 存储需求 bit数 取值范围 备注int 4...
  • Java单元测试和类加载

    千次阅读 2019-12-07 10:25:04
    ​ ⑤测试单元中的每个方法必须可以独立测试,测试方法间不能有任何的依赖 ​ ⑥测试类使用Test作为类名的后缀(不是必须) ​ ⑦测试方法使用test作为方法名的前缀(不是必须) 第二节:注解 注释:给代码...
  • Java中码点和代码单元

    万次阅读 多人点赞 2018-10-26 23:54:39
    码点和代码单元这两个概念还是Java核心技术 卷一》发现的,这也是我看过这本书里面前五章中比较有用的一个知识点(PS:毕竟Java开发都一年了,基础应用都差不多了),以前都没听过。 概念 介绍这个概念之前...
  • java中po层

    千次阅读 2021-02-27 15:11:25
    你看项目用到的就行了,跟着写 ######PO(Persistant Object) 持久对象 用于表示数据库的一条记录映射成的 java 对象。PO 仅仅用于表示数据,没有任何数据操作。通常遵守 Java Bean 的规范,拥有 getter/setter ...
  • 应聘Java开发工程师的基本要求是什么Java程序员的技术水平不同级别要求也不同,分为初级、中级、高级、资深等,不同级别的Java开发工程师企业的要求也是有区别,具体的要求需要结合企业的需求而定。作为一名Java...
  • 首先我们做个小测验,通过下面代码来看看Java语言和Java虚拟机对boolean类型有什么不同: public class Foo { public static void main(String[] args) { boolean flag = true; if (flag) System.out.println(&...
  • Java服务端单元测试指南

    千次阅读 2018-11-01 09:44:37
    Java服务端单元测试指南 作者:墨源,阿里巴巴技术专家 一. 前言 单元测试并不只是为了验证你当前所写的代码是否存在问题,更为重要的是它可以很大程度的保障日后因业务变更、修复Bug或重构等引起的代码变更而...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 230,494
精华内容 92,197
关键字:

在java中什么是最基本的单元

java 订阅