资讯动态

java 学习(二)

发布时间:2026/9/10 22:31:45 来源:尧图企业网站定制
一. 运算符运算符是一种特殊的符号,用以表示数据的运算,赋值和比较等1.算术运算符2. 赋值运算符3. 关系运算符[比较运算符]4. 逻辑运算符5. 位运算符 [需要二进制基础]6. 三元运算符1.1 算术运算符算术运算符是对数值类型的变量进行运算的,在Java程序中使用的非常多注意: java 的运算符 / % public class demo { public static void main(String[] args) { System.out.println(10 / 4);//才从数学来看是2.5,java 中是2. java里: 整数 / 整数, //直接砍掉小数部分 System.out.println(10.0 / 4); //java是2.5 double d 10 / 4 ; //java中是10 / 4 2, 2 2.0; System.out.println(d); //是2.0 // % 取模,取余 // 在 % 的本质 看一个公式 !!!! a % b a - a / b * b // -10 % 3 -10 - (-10) / 3 * 3 -10 9 -1 System.out.println(10 % 3 ); //1 System.out.println(-10 % 3); //-1 System.out.println(10 % -3); //1 // 的使用 int i 10; i; //自增 等价于i i 1; i 11 i; //自增 等价于i i 1; i 12 // 作为表达式使用 // 前 : i先自增后赋值 // 后 : i先赋值后自增 int j 8; //int k j; // 等价于 j j1; kj; //System.out.println(k k j j); //9 9 //int k j; //等价于 k j;jj 1; System.out.println(k k j j); //8 9 } }面试题 :1. 面试题1int i 1;i i ;System.out.println(i); //1问: 结果是多少? 为什么?// 规则使用临时变量:1. temp i;2. i i 1;3. itemp;2. 面试题2int i 1;i i; //规则使用临时变量System.out.println(i) ; //21. i i1;2. tempi;3. itemp;练习题1int i1 10; int i2 20; int i i1; System.out.print(i i); System.out.println(i2 i2); i --i2; System.out.print(i i); System.out.println(i2 i2);第一步: int i i1 ; 后置后置 i 规则 : 先赋值,后自增执行顺序1. 把i1的当前值10 赋值给 i i102. 然后i1 自己加1 i1 11第二步: i --i2; 前置 --前置 -- i 规则: 先自减,后赋值执行顺序:1. 先让i2 自己减 1 i2 20 -1 192. 再把已经自减后的 i2 也就是19 赋值给i i19练习题2 .定义一个变量保存华氏温度,华氏温度转换摄氏温度的公式为: 5/9*(华氏温度 - 100),请求出华氏温度对应的摄氏温度 [234.5]注意: 要考虑数学公式和java语言的特性double huashi123.6 double sheshi 5 / 9 *(huashi-100); System.out.println(sheshi) // 输出0 因为java中 5 / 9 0 整数相除不要小数 // 要修改为 double sheshi 5.0 / 9 *(huashi-100); // 只要运算中有一个是小数类型,低精度要转成相同的高精度1.2 关系运算符1. 关系运算符的结果都是boolean 型,也就是要么是true,要么是false2. 关系表达式经常用在if结构的条件中或循环结构的条件中1.3 逻辑运算符1. 短路与 , 短路或 || , 取反 !2. 逻辑与 , 逻辑或 |, ^ 逻辑异或逻辑运算规则;1. ab: 叫逻辑与, 当a和b同时为true,则结果为true,否则为false2. ab; 叫短路与: 当a和b同时为true,则结果为true,否则为false逻辑与: 左边就算是false ,右边照样执行短路与(会短路), 左边一旦是false 右边直接不执行,跳过3. a|b: |叫逻辑或,规则: 当a和b,有一个为true,则结果为true,否则为false4. a||b: ||叫短路或, 当a和b,又一个为true,则结果为true,否则为falsea | b 逻辑或: 不管左边是true还是false,右边代码一定执行,不会跳过a || b 短路或(会短路): 只要左边已经是true,直接判断结果为true,右边完全不执行(短路跳过)5.!a: 取反,或者非运算, 当a为true,则结果为false,当a为false,结果为true6. a^b 逻辑异或, 当a和b不同时,则结果为true,否则为false1.4 赋值运算符1. 基本赋值运算符 int a;2. 复合赋值运算符,-,*,/,% 等a b; 等价于 a ab;注意: 复合赋值运算符会进行类型转换byte b 3;b 2; //等价 b(byte)(b2);b; // 等价 b(byte)(b1)1.5 三元运算符基本语法 : 条件表达式 ? 表达式1:表达式2;1. 如果条件表达式为true,运算后的结果是表达式1;2. 如果条件表达式为false,运算后的结果是表达式2;int a10;int b99;int result ab?a;b--;1.6 运算符优先级二. 标识符的命名规则和规范1. Java对各种变量,方法和类等命名时使用的字符序列称为标识符2. 凡是自己可以起名字的地方都叫标识符 int num190;标识符的命名规则(必须遵守)1. 由26个英文字母大小写,0-9,_或 $ 组成2. 数字不可以开头,int 3ab 1;3. 不可以使用关键字和保留字,但能包含关键字和保留字4. Java中严格区分大小写,长度无限制,5. 标识符不能包含空格2.1 标识符的命名规则和规范1. 包名: 多单词组成时所有字母都小写: aaa.bbb.ccc2. 类名,接口名: 多单词组成时,所有单词的首字母大写: XxxYyyZzz3. 变量名,方法名: 多单词组成是,第一个单词首字母小写,第二个单词开始每个单词首字母大写: xxxYyyZzz4. 常量名: 所有字母都大写, 多单词的每个单词用下划线链接: XXX_YYY_ZZZ2.2 关键字被java语言赋予了特殊的含义,用做专门用途的字符串 ,关键字中所有字母都为小写2.3 保留字现有java版本尚未使用,但以后版本可能会作为关键字使用,自己命名标识符要避免使用这些保留字byValue,cast,future,generic,inner,operator,outer,rest,var,goto,const2.4 键盘输入语句在编程中,需要接受用户输入的数据,就可以使用键盘输入语句来获取 input.java,需要一个扫描器(对象),就是Scanner1. 导入该类的所在包,java.util2. 创建该类对象(声明变量)3. 调用里面的功能import java.util.Scanner; //表示把java.util下的Scanner类导入 public class demo { public static void main(String[] args) { //演示接受用户的输入 //Scanner类, 表示简单文本扫描器, 在java.util包 //1. 引入/导入 Scanner类所在的包 //2. 创建Scanner对象,new 创建一个对象 //myScanner 就是Scanner类的对象 Scanner myScanner new Scanner(System.in); //3. 接收用户输入 System.out.println(请输入名字); String namemyScanner.next(); //接收用户输入 System.out.println(请输入年龄); int agemyScanner.nextInt(); //接收用户输入 } }三. 四种进制介绍对于整数,有四种表示方式:1. 二进制: 0,1, 满2进1,以0b或0B开头2. 十进制: 0-9, 满10进1.3. 八进制:0-7,满8进1,以数字0开头表示4. 十六进制: 0-9 及A(10)-F(15), 满16进1, 以0x或0X开头表示,此处的A-F不区分大小写int n1 0b1010;int n21010;int n301010;int n40x10101;3.1 二进制,八进制,十六进制转十进制1. 二进制转十进制2.八进制转10进制3. 十六进制转10进制3.2 十进制转二进制,八进制,十六进制1.十进制转二进制注意: 为什么还要在补两个0? 原因是 java里的byte类型时8位二进制,这里是为了凑齐八位2. 十进制转八进制3. 十进制转十六进制3.3 二进制转八进制,十六进制1. 二进制转八进制2. 二进制转十六进制3.4 八进制转二进制,十六进制转二进制1. 八进制转二进制把多余的0去掉2. 十六进制转二进制二进制在运算中的说明1. 二进制是逢2进位的进位制,0,1是基本算符2. 现代的电子计算机技术全部采用的是二进制,因为它只使用0,1两个数字字符,非常简单方便,易于用电子方式实现,计算机内部处理的信息,都是采用二进制数来表示的,二进制(Binary) 数用0和1两个数字及其组合来表示任何数,数位规则是逢2进1,数字1在不同的位上代表不同的值,按从右至左的次序,这个值以二倍递增四. 源码,反码,补码1. 二进制的最高位是符号位: 0表示正数,1表示负数 口诀(0旋转90°还是0 ,1旋转90°等于-*(负数))2. 正数的原码,反码,补码都一样(三码合一)3. 负数的反码 它的原码符号位不变,其他位取反(0-1, 1-0)4. 负数的补码 它的反码1,负数的反码 负数的补码 -15. 0 的反码,补码都是06. java没有无符号数,换言之,java中的数都是有符号的7.在计算机运算的时候,都是以补码的方式来运算的8. 当我们看运算结果的时候,要看他的原码(重点)五. 位运算符5.1 java中有7个位运算符(,|,^,~,,和)分别是 按位与,按位或|,按位异或^,按位取反~,他们的运算规则是:按位与 : 两位全为1,结果为1,否则为0按位或| : 两位有一个为1,结果为1,否则为0按位异或 ^ : 两位一个为0,一个为1,结果为1,否则为0按位取反~: 0 -1, 1-0比如: 1. 2 3 ?2. ~ -2 ?3. ~ 2 ?推导过程 (在计算机运行的时候,都是以补码的方式来运算的)5.1 解 1. 2 3 ?1. 先得到 2 的补码 2.的原码 00000000 00000000 00000000 00000010 ( Java 整数默认是int32 位)2的补码跟源码一样(正数的补码,原码,反码都一样)2. 得到3的补码 3的原码 00000000 00000000 00000000 00000011 补码同样3. 按位 开始运算正数: 运算后的原码也是 (首位符号位,0是正数,1是负数)00000000 00000000 00000000 00000010 2(转成10进制)答案: 25.2 ~ -2 ?1. 先得到-2的补码, 负数的反码等于它的原码符号位不变,其他位取反(0-1, 1-0)-2 原码 10000000 00000000 00000000 00000010-2 反码 11111111 11111111 11111111 11111101-2 补码 11111111 11111111 11111111 11111110(反码1)2. 按位取反~ 0 -1, 1 -0 得 00000000 00000000 00000000 00000001(补码)3. 由于正数三码一样,所以 原码跟补码一样 不用在推导源码 所以00000000 00000000 00000000 00000001 15.3 ~ 21. 先得到2的补码2 原码 00000000 00000000 00000000 000000102 补码 00000000 00000000 00000000 000000102. 按位取反 ~ 11111111 11111111 11111111 11111101 (负数 补码还要在推导出原码)3. 补码- 原码 负数的反码 负数的补码-1 负数原码 负数的反码 符号位不变 其他位取反4. 2的反码 11111111 11111111 11111111 111111005. 2.的原码 10000000 00000000 00000000 00000011 -3 (转十进制 )5.2 位运算符 , 和 运算规则:1. 算术右移 : 低位溢出,符号位不变,并用符号位补溢出的高位2. 算术左移 : 符号位不变,低位补03. 逻辑右移也叫无符号右移,运算规则是: 低位溢出,高位补04. 注意: 没有 符号案例 int a 1 2; // 1 00000001 低位溢出 符号位补溢出的高位 00000000 本质1 / 2 / 20int c 1 2; //1 00000001 00000100 本质1 * 2 *2 4六. 控制结构6.1 顺序控制程序从上到下逐行地执行,中间没有任何判断和跳转顺序控制举例和注意事项Java中定义变量时采用合法的前向引用,如:public class Test{int num1 12 ;int num2 num1 2;}// 错误形式public class Test{int num2 num1 2; //错误int num1 12;}6.2 分支控制 if - else让程序有选择的执行,分支控制有三种1. 单分支if(条件表达式){执行代码块}当条件表达式为true 时, 就会执行{ }的代码,如果为false ,就不执行,说明: 如果{ } 中只有一条语句,则可以不用{ }, 建议写上{ }import java.util.Scanner; public class demo { public static void main(String[] args) { Scanner myScanner new Scanner(System.in); System.out.println(请输入年龄); int age myScanner.nextInt(); if(age 18){ System.out.print(你的年龄大于18岁); } System.out.print(程序继续...); } }2. 双分支if(条件表达式){执行代码块}else{//执行代码块2}import java.util.Scanner; public class demo { public static void main(String[] args) { Scanner myScanner new Scanner(System.in); System.out.println(请输入年龄); int age myScanner.nextInt(); if(age 18){ System.out.print(你的年龄大于18岁); }else{ System.out.print(年龄小于18岁); } System.out.print(程序继续...); } }3. 多分支if(条件表达式){执行代码块}else if{//执行代码块2}......else {//执行代码块n}注意: 多分支可以没有else ,如果所有的条件表达式都不成立,则一个执行入口都没有如果有else, 如果所有的条件表达式都不成立,则默认执行else 代码块6.3 switch 分支结构基本语法:switch(表达式){case 常量1: //当....语句块1;break;case 常量2: //当....语句块2;break;default:default语句块;breack;}1. switch关键字,表示swtich分支2. 表达式对应一个值3. case 常量1: 当表达式的值等于常量1.就执行语句块14. breack: 表示退出swtich5. 如果和case 常量1 匹配,就执行语句块1,如果没有匹配,就继续匹配 case常量26. 如果一个都没有匹配上,执行defaultimport java.util.Scanner; public class Switch01 { public static void main(String[] args) { Scanner scanner new Scanner(System.in); System.out.print(请输入一个字符(a-g)); char c scanner.next().charAt(0); // 获取输入的第一个字符 switch (c) { case a: System.out.println(星期一); break; case b: System.out.println(星期二); break; case c: System.out.println(星期三); break; case d: System.out.println(星期四); break; case e: System.out.println(星期五); break; case f: System.out.println(星期六); break; case g: System.out.println(星期日); break; default: // 输入不是a-g时 System.out.println(输入错误请输入a~g之间的字符); } System.out.println(退出了switch继续执行) } }switch 注意事项和细节讨论表达式数据类型,应和case 后的常量类型一致,或者是可以自动转换成可以相互比较的类型,比如输入的是字符,而常量是intswitch 表达式中表达式的返回值必须是: (byte,short,int,char,enum,String)case子句中的值必须是常量,而不能是变量default子句式可选的,而没有匹配的case时,执行defaultbreak语句用来执行完一个case分支后使程序跳出switch语句块;如果没有写breack,程序会顺序执行到switch结尾switch 和 if 的比较如果判断的具体数值不多,而且符合byte,short,int ,char,enum,Stirng这六种类型,虽然两个语句都可以使用,建议使用swtich语句其他情况: 对区间判断,对结果为Boolean类型判断,使用if,if的使用范围更广6.4 . for循环控制for(循环变量初始化;循环条件;循环变量迭代){循环操作(语句);}for (int i 1; i 10; i) { System.out.print(你好); }注意事项:1. 循环条件式返回一个布尔值的表达式2. for(;循环判断条件;)中的初始化和变量迭代可以写到其他地方,但是两边的分号不能省略int i 1; 循环变量初始化for ( ; i10;){System.out.println(hello i);i;}//无限循环for(;;){System.out.println(ok)}3. 循环初始值可以有多条出事语句,但要求类型一样,并且中间用逗号隔开, 循环变量迭代也可以有多条变量迭代语句,中间用逗号隔开for(int i 0; j 0; i count; i, j 2){System.out.println(i i )}6.5 while循环控制循环变量初始化:while(循环条件){循环体(语句);循环变量迭代;}1. while循环也有四要素2. 只是四要素放的位置和for不一样public class Test { public static void main(String[] args) { int i 1; // 初始值 while (i 5) { // 条件i小于等于5就循环 System.out.println(i); i; // 每次1不然死循环 } } }6.6 do while 循环控制循环变量初始化;do{循环体(语句);循环变量迭代;}while(循环条件);1. do while 是关键字2. 也有循环四要素,只是位置不一样3. 先执行,再判断,也就是说,一定会执行一次4. while 和 do.while 区别举例: 要账public class Test { public static void main(String[] args) { int i 1; do { System.out.println(i); i; } while (i 5); // 分号不能忘 } }6.7 多重循环控制1. 讲一个循环放在另一个循环体内,就形成了嵌套循环,其中,for,while,do...while均可以作为外层循环和内层循环 建议一般使用两层,最多不要超过3层2. 实质上,嵌套循环就是把内层循环当成外层循环的循环体,当只有内层循环的循环条件为false时,才会完全跳出内层循环,才可结束外层的当次循环,开始下一次的循环3. 设外层循环次数为m次,内层为n次,则内层循环实际上需要执行m*n次for(int i 1;i 7;i){for(int j 1;j2;j){System.out.println(ok~~);}}示例. 99乘法表public class demo { public static void main(String[] args) { // i控制行从上往下1~9行 for (int i 1; i 9; i) { // j控制列从左往右1~9列 for (int j 1; j i; j) { System.out.print(j * i (j*i) \t); } System.out.println(); } } }示例 空心金字塔public class demo { //11 9 7 5 public static void main(String[] args) { for (int i1;i10;i) { // 外层控制行 //在输出*之前还要输出空格 for(int k1;k10-i;k){ System.out.print( ); } //控制打印每层的个数 for(int j1;j2*i-1;j){ //空心金字塔 只打印出每行的第一个和最后一个 if(j1 || j2 *i-1||i10){ System.out.print(*);// 不换行 }else{ System.out.print( ); } } System.out.println(); // 一行打完换行 } } }6.8 跳转控制语句 - breack循环,但是循环的次数不知道, -break,当某个条件满足时,终止循环,通过该需求可以说明其它流程控制数据的必要性,比如breakbreak语句用于终止某个语句块的执行,一般使用在switch或者循环[for,while,do-while]中//基本语法{...break;.....}1. 快速入门public class Test { public static void main(String[] args) { for (int i 1; i 10; i) { if (i 5) { break; // 碰到5直接跳出整个for循环 } System.out.println(i); } } }2. 注意事项和细节说明1. break语句出现在多层嵌套的语句块中时,可以通过标签指明要终止的是那一层语句块public class BreakDetail { public static void main(String[] args) { label1: for(int j 0; j 4; j){ label2: for(int i 0; i 10; i){ if(i 2){ break label1; // 直接跳出最外层 label1 循环 } System.out.println(i i); } } } }break语句可以指定退出哪层label1是标签,由程序员指定在实际的开发中,尽量不要使用标签如果没有指定break,默认退出最近的循环体6.9 continue用于结束本次循环,继续执行下一次循环.concinue语句出现在多层嵌套的循环语句体中时,可以通过标签指明要跳过的是哪一层循环,这个和前面的标签的使用的规则一样{....continue;......}示例 输出1-10 跳过5public class TestContinue { public static void main(String[] args) { for(int i 1; i 10; i){ if(i 5){ continue; // i5时跳过下面打印直接下一轮 } System.out.println(i); } } } //输出 1 2 3 4 6 7 8 9 106.10 跳转控制语句 return先简单了解: return 使用在方法,表示跳出所在的方法 ,在讲解方法的时候,会详细的介绍注意: 如果return 卸载main方法,退出程序....public class ReturnTest { public static void main(String[] args) { for (int i 1; i 5; i) { if (i 3) { return; // 直接结束main方法程序退出 } System.out.println(i); } System.out.println(这句不会执行); } }输出: 1 ,2七 . 数组数组可以存放多个同一类型的数据,数组也是一种数据类型,是引用类型,即数组就是一组数据快速入门int[] arr {1,2,3,4,5}; int sum 0; for(int i0; iarr.length; i){ sum arr[i]; } System.out.println(总和sum);7.1 动态初始化1.数组定义数据类型[ ] 数组名new 数据类型[大小]int a [] new int[5]; //创建了一个数组,名字a,存放5个int数组的引用(使用)数组名[下标/索引] 比如: 你要使用a数组的第3个数, a[2]2. 动态初始化先声明数组语法: 数据类型 数组名[ ]; 也可以 数据类型[ ]数组名;int a []; 或者 int [ ] a;创建数组 new语法: 数组名new 数据类型[大小];a new int [10]3. 静态初始化初始化数组语法: 数据类型 数组名[ ] {元素值,元素值}int a [ ] {2,3,4,56,78}7.2 数组的使用注意事项和细节1. 数组是多个相同类型的数据的组合,实现对这些数据的同一管理2. 数组中的元素可以是任何数据类型,包括基本数据类型和引用类型,但是不能混用3. 数组创建后,如果没有赋值, 有默认值int 0short 0,byte 0,long 0,float 0,double 0.0,char \u0000boolean falseString null4. 使用数组的步骤声明数组并开辟空间给数组各个元素赋值使用数组5. 数组的下标是从0开始的6. 数组下标必须在指定范围内使用,否则报: 下标越界异常,比如int [ ] arr new int [5]; 则有效下标为 0 - 47. 数组属引用类型,数组型数组是对象(object)八. 二维数组8.1 初始化二维数组的方式1. 静态赋值, 标准格式int [][] arr{{1,2,3}.{4,5,6}}int[][] arr {{1,2},{3,4},{5,6}};2. 先定行数,列数,后续循环赋值固定行列(规则二维数组,每行长度一致)//3行2列,默认初始值: int0; Stringnull, booleanfalse// 手动给单个位置赋值arr[0][0] 10;arr[1][1] 20;只定义行数,列数动态可变(不规则二维数组,Java特色)每行长度可以不一样,非常灵活://只规定一共3行,每行长度后面自己定int [] [] arr new int[3][];arr[0] new int[2]; //第0行2个元素arr[1] new int[4]; //第1行4个元素arr[2]new int[] {7,8,9}; //第2行直接赋值3. new 关键字同时初始化赋值int [ ][ ] arr new int [ ] [ ]{{11, 22},{33, 44, 55}}4. 先声明.再单独初始化(拆分写)int [ ] [ ] arr;arr new int [2][3];arr[0][0] 1;//或者静态赋值arr new int [ ] [ ] {{1,2},{3,4}};8.2. 杨辉三角import java.util.Scanner; public class demo { public static void main(String[] args) { //杨辉三角 //定义要打印杨辉三角的总行数 int totalRow 10; //1. 创建二维数组: totalRow行, totalRow列 int[][] yangHui new int[totalRow][totalRow]; //外层循环: 遍历每一行 i 代表行下标 for (int i 0; i yangHui.length; i) { // 规则1: 每行第一个元素固定为1 yangHui[i][0] 1; // 规则2: 每行最后一个元素固定为1 对角线位置 ij yangHui[i][i] 1; //内层循环: 给一行中间的数字赋值,j从1开始, 到i-1 结束 // ji 的位置已经赋值为1, 不需要计算 for (int j 1; j i; j) { //规则3: 中间值 上一行左上 上一行正上方 yangHui[i][j] yangHui[i - 1][j - 1] yangHui[i - 1][j]; } } // 修正打印循环放进main方法内部 //循环遍历二维数组, 控制台格式化打印杨辉三角 for (int i 0; i yangHui.length; i) { //只打印当前行有效元素(第i行只有i1 个数字) for (int j 0; j i; j) { System.out.print(yangHui[i][j] \t); } //一行打印完毕,换行 补上分号 System.out.println(); } } // main方法结束大括号 } // 类结束大括号九. 面向对象编程9.1 类与对象9.1.1看一个养猫猫问题张老太养了两只猫猫:一只名字叫小白,今年 3 岁,白色。 还有一只叫小花,今年 100 岁,花色。 请编写一个程序 当用户输入小猫的名字时就显示该猫的名字年龄颜色。如果用户输入的小猫名错误则显示 张老太没有这只猫猫。9.1.2使用现有技术解决 Object01.java1) 单独的定义变量解决2) 使用数组解决现有技术解决的缺点分析:不利于数据的管理效率低》 引出我们的新知识点 类与对象 哲学, 道家思想java 设计者 引入 类与对象(OOP)根本原因就是现有的技术不能完美的解决新的新的需求.// 没有使用Scanner和Random可以删除这两行导入 // import java.util.Scanner; // import java.util.Random; public class demo{ public static void main(String[] args){ // 单独变量来解决 不利于数据的管理 String cat1Name 小白; int cat1Age 3; String cat1Color 白色; String cat2Name 小花; int cat2Age 100; String cat2Color 花色; //数组 数据类型体现不出来, 只能通过下标获取信息, 造成变量名字和内容的对应 //关系不明确,不能体现猫的行为 String[] cat1Arr {小白,3,白色}; String[] cat2Arr {小花,100,花色}; //使用oop面向对象解决 //实例化一只猫[创建一只猫对象] //1. new Cat() 创建一只猫(猫对象) //2. Cat cat1new Cat(); 把创建的猫赋给cat1 //3. cat1 就是一个对象 Cat cat1 new Cat(); cat1.name 小白; cat1.age 3; cat1.color 白色; cat1.weight 10; //创建了第二只猫,并赋给cat2 //cat2 也是一个对象(猫对象) Cat cat2 new Cat(); cat2.name 小花; cat2.age 100; cat2.color 花色; cat2.weight 20; //怎么访问对象的属性 System.out.println(\n面向对象方式); System.out.println(cat1名字 cat1.name 年龄 cat1.age 颜色 cat1.color); System.out.println(cat2名字 cat2.name 年龄 cat2.age 颜色 cat2.color); //调用猫的行为 cat1.meow(); cat2.meow(); } } //使用面向对象方式来解决养猫问题 // 定义一个类, Cat - 自定义的数据类型 class Cat{ //属性/ 成员变量 String name; //名字 int age; //年龄 String color; //颜色 double weight; //体重你代码用到了补上 //猫的行为: 叫 public void meow(){ System.out.println(name 喵喵叫); } }9.1.3. 类与对象的关系1. 类 Class —— 模板、图纸2. 对象 Object —— 根据模板造出来的实例9.1.4 类与对象的区别和联系类是抽象的,概念的,代表一类事务,比如人类,猫类... 即它是数据类型对象是具体的,实际的,代表一个具体事务,即实例类是对象的模版,对象是类的一个个体,对应一个实例9.1.5 对象在内存中存在的形式1. 栈(虚拟机栈,当前方法帧)Cat cat: 在栈中创建引用变量 cat变量里保存地址: 0x0011重点: 栈里不存对象本身,只存对象的地址(引用)2. 堆: 存放new 出来的Cat实例对象new Cat() 在堆开辟一块内存 0x0011 , 这就是Cat实体对象对象内部保存3个成员变量 :1. name: 存地址 0x00222. age: 直接存数值12 基本数据类型3. color: 存地址 0x0033引用类型string 存地址; 基本类型直接存值3.方法区(包含常量池类信息)1. 常量池字符串字面量 小白,白色 存入字符串常量池小白 地址 0x0022白色 地址 0x0033堆内对象的name / color 成员,通过地址指向常量池里的字符串2.加载Cat 类信息类加载后, Cat 的模版信息放在方法区:所有属性定义(name,age,color)所有方法信息区分: 方法区存类的模版, 堆存根据模版new出来的实例9.2 属性/成员变量/字段成员变量 属性field(字段) 即成员变量是用来表示属性的public class demo{ public static void main(String[] args){ } } class Car{ String name;//属性 成员变量,字段 field double price; String color; String[] master; //属性可以是基本数据类型,也可以是引用类型(对象,数组) }9.3 属性是类的一个组成部分, 一般是基本数据类型,也可是引用类型(对象,数组), 比如我们前面定义猫类的int age 就是属性注意事项和细节说明1. 属性定义语法同变量, 示例: 访问修饰符 ,属性类型 属性名;2. 修饰符: 控制属性的访问范围有四种访问修饰符 public,proctected,默认. private3. 属性的定义类型可以为任意类型,包含基本类型或引用类型4. 属性如果不赋值,有默认值,规则和数组一致, 具体说: int 0, short 0, byte 0, long 0, float 0,0,double 0.0 char \u0000,// 编写一个main方法public class demo{ public static void main(String[] args){ //创建Person 对象 // p1 是对象名(对象引用) //new Person() 创建的对象空间(数据) 才是真正的对象 Person p1 new Person(); // 对象的属性默认值,遵守数组规则: System.out.println(\n 当前这个人的信息); System.out.println(age p1.age name p1.name sal p1.sal isPass p1.isPass) ; // 当前这个人的信息 age0 namenull sal0.0 isPassfalse } } class Person { //四个属性 int age; String name; double sal; boolean isPass; }9.3 如何创建对象1. 先声明再创建Cat cat; //声明对象 catcat new Cat() ; //创建2. 直接创建Cat cat new Cat( );9.4 如何访问属性1. 基本语法对象名. 属性名;案例演示赋值和输出cat.name;cat.age;cat.color;9.5 类和对象的内存分配机制1. 栈: 一般存放基本数据类型2. 堆: 存放对象(Cat cat, 数组等)3. 方法区: 常量池(常量,比如字符串), 类加载信息4. java 创建对象的流程简单分析Person p new() Person();p.name jack;p.age 101. 先加载Person 类信息(属性和方法信息, 只会加载一次)2. 在堆中分配空间,进行默认初始化(看规则)3. 把地址赋给p ,p就指向对象9.6 成员方法1. 快速入门添加speak 成员方法,输出我是一个好人添加cal01 成员方法, 可以计算从1 ... 1000的结果添加cal02 成员方法, 该方法可以接受一个数n,计算从1..n 的结果添加getSum 成员方法, 可以计算两个数的和public class demo{ public static void main(String[] args){ Person p1 new Person(); p1.speak(); //调用方法 p1.cal01(); p1.cal02(5); p1.cal02(10); //调用get Sum方法, 同时num1 10; num2 20 //把 方法getSum 返回的值, 赋给变量 return Res int returnRes p1.getSum(10,20); System.out.println(getSum方法返回的值 returnRes); } } class Person { String name; int age; //方法 成员方法 // 1.public 表示方法是公开 // 2.void 表示方法没有返回值 // 3,speak() speak 是方法名 () 形参列表 // 4.{} 方法体, 可以写我们要后自行的代码 // 5.System.oout.println(我是一个好人); 表示我们的方法就是输出一句话 public void speak(){ System.out.println(我是一个好人); } public void cal01(){ //循环完成 int res0; for(int i 1;i1000;i){ resi; } System.out.println(cal01fangfa jisuanjieguores); } //形参列表 , 表示当前有一个形参n 可以接受用户输入 public void cal02(int n){ //循环完成 int res0; for(int i1;in;i){ resi; } System.out.println(cal02方法 计算结果 res); } //添加getSum成员 计算两个数的和 public int getSum(int num1,int num2){ int res num1num2; return res; } }2. 成员方法的好处1. 提高代码的复用性2. 可以将实现的细节封装起来, 然后供其他用户来调用即可访问修饰符 返回数据类型 方法名 (形参列表..) {// 方法体语句;return 返回值;]1. 形参列表: 表示成员方法输入(int n), getSum(int num1,int num2)2. 返回数据类型: 表示成员方法输出,void表示没有返回值3. 方法主体: 表示为了实现某一功能代码块4. return 语句不是必须的9.7 注意事项和使用细节1.2. 访问修饰符(作用是控制 方法使用的范围)如果不写默认访问, 有四种: public, protected, 默认,private, 具体后面说3. 返回数据类型1, 一个方法最多有一个返回值 思考,如何返回多个结果,返回数组2. 返回类型可以为任意类型,包含基本类型或引用类型(数组,对象)3. 如果方法要求有返回数据类型,则方法体中最后的执行语句必须为retrun值;而且要求返回值类型必须和return 的值类型一致或兼容4. 如果方法是void, 则方法体中可以没有return 语句,或者只写return;public class demo { public static void main(String[] args) { A a new A(); // 测试调用加上这两句可以看到执行效果 a.sayOk(); a.m1(); } } class A { public void print(int n) { System.out.println(print()方法被调用 n n); } public void sayOk() { // sayOk调用print本类直接调用 print(10); System.out.println(继续执行sayOK()~~~); } //跨类中的方法A调用B类方法: 需要通过对象调用 public void m1() { System.out.println(m1() 方法被调用); B b new B(); b.hi(); System.out.println(m1() 继续执行); } } class B { public void hi() { System.out.println(b类中的hi() 被执行); } }9.8 基本数据类型的传参机制1. 基本数据类型: 传递的是值(值拷贝), 形参的任何改变不影响实参public class demo { //编写一个main方法 public static void main(String[] args){ int a10; int b20; //创建AA对象, 名字 obj AA obj new AA(); } } class AA{ public void swap(int a, int b){ // a10 b10 //完成了 a 和 b 的交换 int tmpa; a b; b tmp; /// a20 b10 } }2. 数据类型的传参机制1. 看一个案例 MethodParameter02. javapublic class demo { //编写一个main方法 public static void main(String[] args){ int a10; int b20; //创建AA对象, 名字 obj AA obj new AA(); } } class AA{ public void swap(int a, int b){ // a10 b10 //完成了 a 和 b 的交换 int tmpa; a b; b tmp; /// a20 b10 } }解析:1. int a, intb, 是基本数据类型2. 调用obj.swap(a,b) 的时候;不是把main里的a,b 本身传给swap, 而是拷贝一份a10, b20的副本,传入swap方法3. swap 里面交换的,只是副本swap 内部: 副本a 和副本b 成功交换方法执行完毕, swa栈帧销毁,副本直接消失main方法里面原始的a10, b20 完全不受影响,不会交换!内存角度拆解main方法进栈: 栈中开辟空间, 存放a10,b20调用swap: 新建一块swap栈空间,复制一份a10,b20swap 内部交换复制出来的两个变量swap 就内部交换复制出来的两个变量回到main: 原来的a,b 还是10,20关键结论:1. Java 只有值传递,没有引用传递2. 基本类型作为方法参数: 传递的是 数据副本,方法内部修改不会影响外面原始变量3. 如果是引用类型,数组,对象作为参数, 传递的是: 地址副本,通过地址修改对象内部属性会影响外面,因为副本和外面的变量,存的是同一个对象地址2. MethodParameter02 .java1. 基本数据类型public class demo { public static void main(String[] args) { //在对内存 new 出一个Person 对象 //main栈里创建局部变量p, p保存这个对象的内存地址 Person p new Person(); p.name jack; p.age 10; //创建B类对象 B b new B(); //把main中p存的地址值拷贝一份 传进去 b.test200(p); System.out.println(main 的 p.age p.age); } } class Person { String name; int age; } class B { public void test200(Person p) { //1. 修改对象的属性 // p.age10000; p.age10000 main里的p方法内形参p保存同一个对象地址,修改堆中对象属性,外面生效 //2. 方法内new 一个新Person 对象 //关键点 形参p指向全新对象 // p new Person(); // p.nametom; // p.age99; //此时main的 p.age10 //pnew Person() 只是方法内部副本变量p指向新对象, main那边的p丝毫没变, 依旧指向jack //3.方法内部p null p null ; // 副本变量质控 main 的 p.age10 仅仅把副本变量清空,外面main的p完全不受影响 } }// 对象类型public class demo { public static void main(String[] args) { int [] arr {1,2,3}; B b new B(); //调用test100方法 把 数组arr地址值传给形参arr //注意: 不是把(1,2,3) 复制一份, 两个arr指向堆里面同一个数组! b.test100(arr); System.out.println(main的 arr数组 ); for(int i0;iarr.length;i){ System.out.print(arr[i] \t); } } } class B { public void test100(int[] arr){ //修改数组第一个元素arr[0] 200 //因为两处引用指向同一堆数组 //此处修改后,main里面的数组内容也跟着改变! arr[0]200; System.out.println(test100 的arr数组); for(int i0; iarr.length; i){ System.out.print(arr[i] \t); } } }9.9 . 成员方法返回类型是引用类型应用实例1. 编写一个Mytools 类,编写一个方法可以打印二维数组的数据2, 编写一个方法copyPerson, 可以复制一个Person对象,返回复制的对象,科隆对象,注意要求得到新对象和原来的对象是独立的对象,只是他们的属性相同public class demo { public static void main(String[] args) { Person p new Person(); p.name milan; p.age 100; //创建tools MyTools tools new MyTools(); Person p2 tools.copyPerson(p); //到此 p 和p2 是 person 对象, 但是是两个独立的对象,属性相同 System.out.println(p的属性 age p.age 名字 p.name); System.out.println(p2的属性 age p2.age 名字 p2.name); //可以同对象比较看看 System.out.println(pp2); //false } } //类 模版 class Person { String name; int age; } //类 工具类 方法 class MyTools { //编写一个方法copyPerson 可以复制一个Person对象,返回复制的对象,克隆对象, // 注意要求得到新对象和原来的对象是两个独立的对象,只是他们的属性相同 //编写方法的思路 //1.方法的返回类型Person //2.方法的名字 copyPerson //3.方法的形参(Person p) //4.方法体,创建一个对象,并复制属性,返回即可 public Person copyPerson(Person p) { //创建一个新的对象 Person p2 new Person(); p2.name p.name; // 把原来对象的名字赋给p2.name p2.age p.age; // 把原来对象的年龄赋给p2.age return p2; } }

读完文章,也想定制专属网站?

尧图设计师 24 小时内与您沟通定制方案

免费获取报价