1.1运算符与键盘录入
注意两数相除
/*
算数运算符:
+
-
---------------------------------------------------------------------
*:
/:整数相除,结果只能得到整数,想得到带有小数的结果,需要有小数参与运算
% 取模 作用:取余数
问题:这玩意儿有什么用?
回答:% 目前能够想到的场景,可以进行奇偶的判断
- 任何一个数%2的结果,不是0,就是1
*/
给一个数(123)想获得个位,十位,百位,上的数字
/* 个位的计算:
数值%10
123除以10(商12,余数是3);
十位的计算:
数值/10%10
123除以10(商12,余数为3);
商12再模以10(商1,余数为2)
百位的计算:
数值/10/10%10
123/10/10%10(123/10得到12,12/10得到1,1%10得到1) 以此类推
*/
1.1.2计算机中进制的分类
计算机中进制的分类:
十进制:默认
二进制:0b开头
八进制:0开头
-今后编写数值,尽量不要以0开头
十六进制:0x开头
-今后看到一组数据是0~9,字母a~f组合排列的,要知道这是16进制数据.
二进制到十进制转换
公式: 系数*基数的权次幂 累加起来
系数:就是每一位上的数
基数:当前进制数
权:从右往左,依次为 0 1 2 3 4 5 6....@8421快速转换法
二进制中,每一位的1都是代表一个固定的数值
把每一位的1代表的十进制加起来得到的结果就是它所代表的十进制数.1 1 1 1 1 1 1 1
128 64 32 16 8 4 2 1
原码,反码,补码 以及强转过程的精度损失
@原码:
数据的二进制体现形式,一个字体由8个二进制组成
高位:二进制数据中,最左侧的数据,通过高位代表符号位
0代表正数
1代表负数
其余位,表示数值大小
弊端:遇到负数运算,就会出现错误(计算机在运算的时候,都是以二进制补码的形式在运算)
@反码:
正数的反码与原码相同
负数的反码是对原码逐位取反,但符号位除外.
@补码:
正数的补码与其原码相同
负数的补码是在其反码的末尾加1
*/
// 原码:1 0 0 0 1 0 1 0
// 反码:1 1 1 1 0 1 0 1
// + 1
//----------------------------------
// 补码:1 1 1 1 0 1 1 0
/*
强转中的精度损失:
int a=130;
byte b=(byte)a; //-126!整数130:默认为int,int 占用4个字节,也就是4组8个二进制位
00000000 00000000 00000000 10000010
!强转到byte:4个字节,强制转换位1个字节,就是砍掉前3组8位
10000010 (此时为补码(正数的原反补都是一样的)(符号位为1 代表负数))
!根据运算后的补码,反推原码
*/
//!!!!!!! (原码到补码的转换:取反再加1)
//!!!!!!! (补码到原码的转换:还是取反再加1)
// 补码: 1 0 0 0 0 0 1 0
// +1:反码: 1 1 1 1 1 1 0 1
//---------------------------------------
// 二进制原码: 1 1 1 1 1 1 1 0
// 8421码:
//- 64 32 16 8 4 2 1
// 拼上符号为即是-126
// 这就是为什么int 130强转为byte后为-126
1.1.3 Scan 键盘录入步骤
Scanner 键盘录入的三个步骤
1.找符咒
代码:import java.util.Scanner;
位置:class上面
含义:能让自己的类ScannerDemo,从代码仓库中,找到Scanner符咒2.召唤精灵
代码:Scanner sc=new Scanner(System.in)
位置:main方法里面
含义:从符咒里召唤精灵,给精灵取名叫sc3.指挥精灵干活
代码:
int age=sc.nextInt();
double height=sc.nextDouble();
boolean flag=sc.nextBoolean();
String name=sc.next();
1.1.6类型转换 面试
类型转换面试题:下列代码是否存在错误,如果有,请指出说明,并改正. byte b1=3; byte b2=4; byte b3=b1+b2; 错误原因: b1和b2是两个byte类型,在运算的时候,会提升为int类型 提升之后,就是两个int在运算了,运算的结果还是int. 将int类型的结果,赋值给byte类型的变量,属于大给小,不能直接给. byte b1=3; byte b2=4; byte b3=(byte)(b1+b2); System.out.println(b3); 还没结束 请问 byte b=3+4 是否可以通过编译,如果是,请问为什么? byte b=3+4; 错误答案: 某同学:这里的3和4是两个字面量,之前说过,所有整数默认都是int类型,所以这里应该是两个int做运算 运算后的结果还是int,int类型结果给byte类型变量赋值,大的给小的,不能直接给,编译错误. 正确思路: Java存在常量优化机制:在编译的时候(javac)就会得到3和4两个字面量或者说常量进行运算,可以通过编译. 产生的字节码文件:byte: b=7;(编译时就进行3+4的运算了,到了字节码文件中就会=7) 前面的 byte b3=b1+b2; b1 b2 是变量 不是 字面量(常量) 所有不可以通过编译
1.1.7 类型转换
(小的会提升成大的)
类型转换-隐式转换
介绍:将取值范围小的数据或变量,给取值范围大的变量赋值,可以直接赋值
-简单记:小的给大的,可以直接给(指的是取值范围)
取值范围从小到大
byte-->short->int->long->float->double
问题:float 占用4个字节,为什么放在了long(8个字节)的后面
解释:虽然float占用了4个字节,但是[取值范围]要比8个字节的long更大
-小数的二进制存储形式,要更加节省内存运算过程中的隐式转换
*取值范围小的数据,和取值范围大的数据进行运算,小的会想提升大的之后,再进行运算
*byte short char 三种数据在运算的时候,都会提升为int,然后再进行运算int a=10;
double b=12.3;
double c=a+b;byte a=10;
byte b=5;
int c=a+b;int a=1;
char b='a';
int c=a+b;
System.out.println(c); 98
强制转换介绍
*把一个取值范围大的数值或变量,赋值给另一个取值范围小的变量,不允许直接赋值,需要加入强转
注意:强制转换[有可能]会出现精度损失
1.1.8 基本数据类型
1. 基本数据类型
整数
byte 1个字节 -128~127
short 2个字节
int 4个字节
long 8个字节
小数
float(单精度) 4个字节
double(双精度) 8个字节
字符
char 2个字节
布尔
boolean 1个字节
2个引用数据类型
-----------------------------------------------------
使用思路:
1.整数类型:
首选int,如果发现int装不下,将类型换成long,定义long类型变量需要加入L标识2.小数类型:
首选double,非要用float类型,需要加入F标识
/*
变量的注意事项:
1.变量名不允许重复定义
2.一条语句可以定义出多个变量,中间要使用逗号分隔
3.变量在使用之前,必须完成赋值
4.TODO:变量的作用域(未完待续)
1.1.8 方法介绍
方法(函数)介绍:一段具有独立功能的代码块,不调用就不执行.
好处:
1.可以将原本挤在一起的臃肿代码,按照功能做分类管理.
2.提高了代码的复用性
定义格式:
public static void 方法名(){
方法体(逻辑代码)
}
方法的调用格式:
方法名();
注意事项:
1.方法与方法之间是平级关系,不允许嵌套定义
2.方法不调用就不会执行
3.方法的定义顺序,和执行顺序无关,想要梳理执行顺序,就看调用顺序
1.1.9 赋值运算符
/*
赋值运算符:
1.基本运算符
=:将符号右侧的数据,赋值给左边的变量
int num=10;
2.扩展赋值运算符
+=:将符号左右两边的数据,做加法运算,再将结果赋值给左边.
-=:将符号左右两边的数据,做减法运算,再将结果赋值给左边.
*=:将符号左右两边的数据,做乘法运算,再将结果赋值给左边.
/=:将符号左右两边的数据,做除法运算,再将结果赋值给左边.
%=:将符号左右两边的数据,做取模运算,再将结果赋值给左边.
int num =10;
num +=20;
System.out.println(num);
----------------------------------------------------------------------------
细节补充:
扩展赋值运算符,内部自带强转效果
short s=1;
s=s+1;//(会报错)
s=(short)(s+1);(得改成)
System.out.println(s);
public static void main(String[] args) {
double a=12.3;
int b=10;
b+=a; //22.3
System.out.print(b); //22
}
1.1.10 关系运算符(比较运算符)
关系运算符(比较运算符)
>
>=
<
<=
==
!=
1.1.11 逻辑运算符
逻辑运算符 :
1. 用于连接boolean类型的表达式, 或者是值
2. 整合多个条件, 为一段整体的逻辑分类:
&(与) : 并且, 遇false, 则false
场景: 范围性的判断查找
举例: 键盘录入一个学生成绩, 判断该成绩是否是90~100之间
伪代码: 不能运行, 仅供理解
int score = 95;
如果(score >= 90 & score <= 100){
}|(或) : 或者, 遇true, 则true
场景: 多个条件任选其一
举例: 键盘录入一个学生学号, 学号 3 5 12int id = 3;
如果(id == 3 | id == 5 | id == 12){
}!(非) : 取反
场景: 对一段逻辑整体做取反操作
举例: 键盘录入一个学生学号, 学号除了 3 5 12 都要
如果( ! (id == 3 | id == 5 | id == 12) ){
}
^(异或) : 相同为false, 不同为true
1.1.12 短路逻辑运算符
或,与,非
public class OperatorDemo5 {
/*
短路逻辑运算符 :& : 没有短路效果, 无论左边是true, false, 右边都要继续执行
&& : 具有短路效果, 左边为false, 右边不执行了
左边为true, 右边要继续执行| : 没有短路效果, 无论左边是true, false, 右边都要继续执行
|| : 具有短路效果, 左边为true, 右边不执行了
左边为false, 右边要继续执行--------------------------------------------------- 常用的逻辑运算符: && || !
*/
}
public static void main(String[] args) {
int x = 3;
int y = 4;
// false
boolean result = ++x > 5 && y-- < 4;
System.out.println(x); // 4
System.out.println(y); // 3
System.out.println(result); // false
}
1.1.13 方法重载关系的要求
方法重载关系的要求
在同一个类中,定义了多个同名的方法
但每个方法有不同的参数类型或参数个数,这些同名的方法,就构成了重载关系(方法与方法之间的关系)
简单记:同一个类中,方法名相同,参数不同的方法
参数不同:个数不同,类型不同,顺序不同注意:识别方法之间是否重载关系,只看方法名和参数,跟返回值(void,int...)无关.
*//*
方法重载(Overload):方法与方法之间的一种关系
目标1: 能够独立识别除方法与方法之间,是否是正确重载
- 在同一个类中,方法名相同,参数不同,与返回值无关
-参数不同:1.类型不同 2.个数不同 3.顺序不同
目标2: 能够理解方法重构带来的好处-不需要记忆过多繁琐的方法名字了
1.1.13方法的补充
定义方法时,要做到两个明确
明确参数:主要是明确参数的类型和数量
明确返回值类型
1.2 if 与循环结构
1.1.15 break和continue
1.1.16 control 死循环
无限循环(死循环)
1.for(;;){}
2.while(true){}
3.do{}while(true);
1.1.17 do while 循环
//特点:无论判断条件是否满足都至少执行一次循环体
do...while循环格式:
初始化语句;
do{
循环体语句;
条件控制语句;
}while(判断条件);
执行流程:
1.执行初始化语句
2.执行循环体语句
3.执行条件控制语句
4.执行判断条件,看起返回结果是true,false
false:循环结束
true:回到第二步继续
public static void doWhileTest() {
for (int i = 1; i <= 5; i++) {
System.out.println("程序员");
}
System.out.println("***************************");
int i = 1;
do {
System.out.println("程序员");
i++;
}
while(i <= 5) ;
}
1.1.18 for 循环
for 循环语句格式:
for(初始化语句;判断条件;条件控制语句){
循环体语句;
}
执行流程:
1.执行初始化语句,在整个循环过程中,只执行一次
2.执行判断条件,看其返回结果是true,false
false:循环结束
true:执行第三步
3.执行循环体语句
4.执行条件控制语句
5.回到2继续...
for 循环注意事项:
1.for循环{}中定义的变量,在每一轮循环结束后,都会从内存中释放
2.for循环()中定义的变量,在整个循环结束后,会从内存中释放
3.for循环()和{}之间不要写分号
public static void print() {
for (int i = 1; i <=10; i++) {
System.out.println("跑圈");
}
}
public static void forTest2(){
//快捷键 5.fori+回车
for (int i = 0; i < 5; i++) {
//i=0,1,2,3,4(默认i从零开始)
}
}
for循环 : 用于控制循环的那个变量, 在循环结束后, 就会从内存中消失, 循环结束后, 不能继续使用
while循环 : 用于控制循环的那个变量, 在循环结束后, 不会从内存中消失, 循环结束后, 可以继续使用
1.1.19 while 循环
while循环格式:
初始化语句;
while(判断条件){
循环体语句;
条件控制语句;
}执行流程:
1. 执行初始化语句
2. 执行判断条件, 看其返回结果是true, false
false : 循环结束
true : 进入第三步
3. 执行循环体语句
4. 执行条件控制语句
5. 回到2继续
1.1.20 if 语句
1.1.21 switch 语句
switch语句格式 :
switch (将要匹配的值) {
case 值1:
语句体1;
break;
case 值2:
语句体2;
break;
case 值3:
语句体3;
break;
...
default:
语句体n+1;
break;
}执行流程:
1. 拿着 () 中将要匹配的值, 跟case给出的选项, 逐个进行匹配
匹配成功, 执行对应的语句体, 再由break结束掉整个的switch语句2. 如果给出的所有case, 都匹配失败了, 将会执行最后的 default, 由break结束掉整个的switch语句
注意事项:
switch语句注意事项 :
1. case 后面的值不允许重复
2. case 后面的值, 只能是字面量, 不能是变量
3. switch () 中可以接收的类型1). 基本数据类型: byte short char int
2). 引用数据类型: jdk5版本开始可以是枚举, jdk7版本开始可以是String字符串4. case穿透现象
穿透现象:
public static void switchTest3(){
Scanner sc = new Scanner(System.in);
System.out.println("请输入:");
int week = sc.nextInt();
switch(week){
case 1, 2, 3, 4, 5 -> System.out.println("工作日");
case 6, 7 -> System.out.println("休息日");
default -> System.out.println("您的输入有误");
}
}
}
sb的编码形式:
public static void switchTest2(){
int week = 1;
String num = "1";
switch (num) {
case "1" :
System.out.println("星期一");
break;
case "2" :
System.out.println("星期二");
break;
case "3" :
System.out.println("星期三");
break;
default:
System.out.println("您的输入有误");
break;
}
}
1.1.22 random 随机数
//需求:产生20~80之间的随机数
public class RandomDemo {
public static void main(String[] args) {
randomTest();
}
/*
Random 产生随机数
*/
public static void randomTest(){
//2.召唤精灵
Random r=new Random();
//3.指挥精灵产生随机数
/*for (int i = 1; i <= 20; i++) {
int num =r.nextInt(100)+1;
System.out.println(num);
}*/
//需求:产生20~80之间的随机数
Random rc=new Random();
for (int i = 1; i <= 60; i++) {
//0~60+20
int num=rc.nextInt(61)+20;
System.out.println(num);
}
}
}
1.1.23 循环练习实例
需求:求1~100之间的偶数和,并把求和的结果打印在控制台
分析:
1.定义求和变量sum,准备记录累加的结果
2.使用for循环,分别获取数据1-100
3.循环中加入if语句,筛选除偶数数据
4.将每一个偶数数据,和sum变量进行累加
5.循环结束后,打印求和后的结果
//1.定义求和变量sum,准备记录累加的结果
int sum = 0;
//2.使用for循环,分别获取数据1-100
for (int i = 1; i <= 100; i++) {
//i:1~100之间的每一个数据
//3.在循环加入if语句,筛选除偶数数据
if (i % 2 == 0) {
//4.累加求和
sum = i + sum;
return sum;
}
}
/*需求:在控制台打印出99乘法表
1*1=1
1*2=2 2*2=4
1*3=3 2*3=6 3*3=9
1*4=4 2*4=8 3*4=12 4*4=16
1*5=5 2*5=10 3*5=15 4*5=20 5*5=25
...
建议初学步骤:
1.9行9列的矩形
2.9行的直角三角形
3.99乘法表
public static void print99(){
for (int i=1;i<=9;i++){
System.out.println();
for(int j=1;j<=i;j++)
System.out.print(j+"*"+i+"="+i*j+"\t");
}
}
}
1.1.24 if 语句练习实例
1.1.25 random 随机数练习实例
1.1.26 while 循环练习实例
1.3 数组
1.1.27 需求:排序数组
//需求:(从小到大)排序数组
public static void main(String[] args) {
Scanner reader=new Scanner(System.in);
//定义实参数组
double arr[];
System.out.println("请输入要排序数组的长度");
int n=reader.nextInt();
arr=new double[n];//初始化数组
//创建排序对象sortNumber1
SortNumber1 sortNumber1=new SortNumber1();//初始化对象sortNumber1
//为实参数组赋值
for (int i=0;i<arr.length;i++){
System.out.println("请输入第"+(i+1)+"个数");
arr[i]=reader.nextDouble();//这段代码是在Java中使用Scanner对象的nextDouble()方法来读取用户输入的一个double类型的值,并将其赋值给数组arr的第i个元素。换句话说,这行代码是用来从控制台输入读取一个double类型的值,并将其存储到数组arr的第i个位置上。
}
//将实参数组的应用传递给形参数组
sortNumber1.sortArray(arr);
//输出数组
for(double num:arr){
System.out.println(num);
}
}
}
class SortNumber1{
//数组排序
void sortArray(double numArray[]){
for (int i=0;i<numArray.length-1;i++){ //仔细思考length-1
for (int j=i+1;j<numArray.length;j++){
if(numArray[i]>numArray[j]){
double temp=numArray[i];
numArray[i]=numArray[j];
numArray[j]=temp;
}}}}}
1.1.28 传值
public class ArgsTest1 {
//课程在黑马的Day5_06 14:50
public static void main(String[] args) {
int number = 100;
//变量在内存中就会占字节空间
System.out.println("调用change方法前:" + number); // 100
change(number);
System.out.println("调用change方法后:" + number); // 100
}
public static void change(int number) {/*这个方法有形参,形参对于方法而言
就是个变量而已,变量就会占空间*/
number = 200;
}
}
与上述代码区别 change中有个return
//数组记录的是一份地址!
/*
方法的参数传递问题
方法的参数 如果是基本数据类型 那么在传参的时候
真正所传过来的就是具体的数值
*/
public class ArgsTest1_1 {
public static void main(String[] args) {
int number = 100;
System.out.println("调用change方法前:" + number);
//int result=change(number),这是找了一个新变量来接收
number = change(number);//用已有的number接着做接收
//方法有形参,形参对于内存来讲是变量
System.out.println("调用change方法后:" + number);
}
public static int change(int number) {
number = 200;
return number;/*在哪调的方法,结果就会回到哪里去
这里是change调的,就会回到change()中
*/
}
}
//运行结果:
调用change方法前:100
调用change方法后:100
注意比较与下面数组的区别
//方法 栈内存 堆内存
//方法的参数,传递的是引用数据类型的时候,它真正所传递的是地址值
public class ArgsTest2 {
/*
方法的参数传递问题 :
1. 基本数据类型: 传递的是数据值
2. 引用数据类型: 传递的是地址值
问题: Java到底是值传递, 还是址传递?
回答: 值传递, 地址值也是值
*/
public static void main(String[] args) {
int[] arr = {11, 22, 33, 44, 55};
System.out.println("调用change方法之前:" + arr[0]); // 11
change(arr);
System.out.println("调用change方法之后:" + arr[0]); // 66
}
public static void change(int[] arr) {/*
这个方法是有形参的,形参对于内存来讲是变量,变量就要占空间
change也会开辟一个空间
空间中也有一个int[] arr
主方法会将arr的地址给change一份(两个人两根链子牵着同一只狗)*/
arr[0] = 66;
}
//return后 主方法里面别忘了找一个变量做接收
}
展开讲解 java中的参数传递 按 值 还是 按引用
我的理解: 一个是传 字面量(数字),一个是传地址值 数字是值 ,地址值也是值呀!
1.1.29 数组介绍
数组介绍:一种容器,可以存储同种数据类型的多个值
数组的使用场景:发现手里的数据有多个,并且这多个数据还属于同一数组
就可以考虑使用数组容器进行维护
初始化:再内存中,为数组开辟空间,并将数据存入容器的过程数组的定义格式:
1.数据类型[] 数组名;
2.数据类型 数组名[];
注意:
这种定义格式,定义出来的,只是数组的类型的变量而已,
内存中还没有创建出数组容器.
*/
public static void arrayTest1() {
int[ ] array;
int array2[ ];
//System.out.println(array);
//System.out.println(array2);
}/*
数组的静态初始化格式:
1.完整格式:
数据类型[ ] 数组名=new 数据类型[]{元素1,元素2,元素3...}
2.简化格式:
数据类型[ ] 数组名={元素1,元素2,元素3...};
打印数组名:
[I@4eec7777
@:分割符
[:当前空间,是数组类型的
I:当前数组类型,是int型
4eec7777:数组的十六进制内存地址
*/
public static void arrayTest2(){
int[ ] arr1={11,22,33};
double[ ] arr2={11.1,22.2,33.3};
System.out.println(arr1);
System.out.println(arr2);
}
}
//运行结果
[I@4eec7777
[D@3b07d329
1.1.30 数组元素访问格式:
1.1.31 数组的动态初始化
数组的动态初始化:
在初始化的时候,只需要指定数组的长度,系统就会分配默认值(初始值)格式:数据类型[] 数组名=new 数据类型[长度];
不同数据类型 默认值不同
默认值的分类 :
整数 : 0
小数 : 0.0
布尔 : false
-----------------------------------------------------
字符 :'\u0000' ---> Unicode字符---> 常见的体现是空白字符
引用数据类型 : null
引用数据类型有哪些呢?
有 数组, 类, 接口
String本质来讲就是一个类(按ctrl 鼠标左键点一下这个string
1.1.32 二维数组
细节: 二维数组在存储一维数组的时候, 具体存储的是一维数组的地址值
二维数组的元素访问格式 :
数组名[m索引][n索引] :
m索引 : 指定访问哪一个一维数组
n索引 : 访问一维数组中的哪一个元素
1.1.33 二维数组的动态初始化
二维数组动态初始化 :
格式: 数据类型[][] 数组名 = new 数据类型[m][n];
m : 这个二维数组中, 可以存放多少个一维数组
n : 每一个一维数组中, 可以存放多少个元素
1.1.34 二维数组的访问格式
细节: 二维数组在存储一维数组的时候, 具体存储的是一维数组的地址值
二维数组的元素访问格式 :
数组名[m索引][n索引] :
m索引 : 指定访问哪一个一维数组
n索引 : 访问一维数组中的哪一个元素
1.1.35 数组索引越界异常
数组索引越界异常 : ArrayIndexOutOfBoundsException
原因: 访问了不存在的索引
1.1.36 空指针异常
空指针异常 : NullPointerException
原因: 当引用数据类型的变量, 被赋值为null之后, 就代表跟堆内存的连接被切断了
这时候还想去访问堆内存的数据, 就会出现空指针异常
(相当于你牵着一条狗,null就是一把菜刀,把你牵狗的绳子切断了)
1.1.37 静态初始化与动态初始化的两种区别
数组两种初始化的区别:
动态初始化:手动指定长度,系统分配默认初始化值
静态初始化:手动指定元素,系统会根据元素的个数,计算出数组的长度两种初始化的使用选择:
1.静态初始化:
如果要操作的数据,需求中已经明确给出了,直接静态初始化
需求:已知班级学生成绩为:100,90,100,20,100,找出最高分
int[] arr={100,90,100,20,100}
2.动态初始化:
只明确元素个数,不明确具体数值
需求1:键盘录入5个学生成绩,找出最高分
需求2:产生10个1~100之间的随机数,找出最小值int[] arr={???}//错误
int[] arr=new int[5];//正确,得先动态初始化
1.1.43 数据交换
面试题: 实现两个变量的数据交换, 不允许定义第三方变量
定义第三方变量的大家都会
int a = 10;
int b = 20;int c = a;
a = b;
b = c;System.out.println("a=" + a); // 20
System.out.println("b=" + b); // 10
不定义第三方变量呢?
^ 异或 :
特点:
1. 相同为false, 不同为true
2. 一个数字, 被另外一个数字异或两次, 该数本身不变异或操作数值的运算过程 :
1. 将需要运算的数据, 转换为二进制数据
0000 1010 10
0000 0101 52. 将二进制数据的0当做为false, 1当做为true, 运算
0000 1010
^ 0000 0101
--------------------
0000 11113. 将运算后的二进制数据, 转换为十进制
1.1.44 需求:打印逢7则过的数据
需求:在控制台打印出1~100之间满足封七过的规则的数据
分析:
1.通过循环获取到1~100之间的每一个数字
2.数值拆分,拆分出个位和十位
3.根据规则加入if判断
if(ge==7 || shi==7 || i % 7==0)
4.打印出满足规则的数据
1.1.45 需求:输出数组元素和
需求:
有这样的一个数组,元素是{68,27,95,88,171,996,51,210}
求出该数组中满足要求的元素和
要求是:求和的元素个位和十位都不能是7,并且只能是偶数
public static void main(String[] args) {
int[] arr={68,27,95,88,171,996,51,210};
int evenNumberSum = getEvenNumberSum(arr);
System.out.println("元素和为:"+evenNumberSum);
}
public static int getEvenNumberSum(int[] arr){
//1.定义一个求和变量
int sum=0;
//2.变量数组,获取到内部的每一个元素
for (int i = 0; i < arr.length; i++) {
int ge=arr[i]%10;
int shi=arr[i]/10%10;
if (ge!=7 && shi!=7 && arr[i]%2==0){
//System.out.println(arr[i]);
//求和操作
sum+=arr[i];
}
}return sum;
}
1.1.46 需求:比较数组内容
需求:定义一个方法,比较两个数组的内容是否相同
要求:长度,内容,顺序完全相同
提示:
==:
1.基本数据类型:比较数据值
2.引用数据类型:比较地址值
public static void main(String[] args) {
int[] arr1={11,33,22};
int[] arr2={33,22,33};
boolean b = checkArrayContent(arr1, arr2);
System.out.println(b);
}
public static boolean checkArrayContent(int[] arr1,int[] arr2){
//1.比较数组的长度
if (arr1.length!=arr2.length){
return false;
}
/*代码要是能够走到这里,代表数组的长度肯定是相同的
数组的长度相同,意味着索引是相同的*/
//比较数组中的元素内容
for(int i=0;i<arr1.length;i++){
if(arr1[i]!=arr2[i] ){
return false;
}
//如果代码走到这里,代表两个数组长度,内容,顺序完全相同
}return true;
}
1.1.47 需求:查找数组元素索引位置
需求:
设计一个方法,查找元素在数组中的索引位置
(其实是查找元素,在数组中第一次出现的索引位置)
已知一个数组arr={19,28,37,46,50};
键盘录入一个数据,查找该数据在数组中的索引.
并在控制台输出找到的索引值
如果没有查找到,则输出-1
public static void main(String[] args) {
int[] arr={19,28,37,46,50};
Scanner sc=new Scanner(System.in);
int num= sc.nextInt();
int index = genIndex(num, arr);
System.out.println(index);
}
public static int genIndex(int num,int[] arr){
//1.假设要查找的元素,在数组中就是不存在的
int index=-1;
//2.遍历数组,获取内部的每一个元素
for (int i = 0; i < arr.length; i++) {
//3.比较
if (arr[i]==num){
//4.找到了,让index变量记录正确的索引位置
index=i;//不是index=num 因为需求是要索引位置不是数字
break;
}
}
return index;
1.1.48 需求:查找数组元素索引位置(考虑重复问题)
需求:设计一个方法,查找元素在数组中的索引位置(考虑重复元素问题)
注意:return只能返回一个结果(提示:没有类型的限制)
提示:当一个方法运行结束后,有多个结果需要返回,要怎么处理?
回答:可以将多个结果,存入一个数组容器,将数组返回
public static void main(String[] args) {
Scanner sc =new Scanner(System.in);
int num= sc.nextInt();
int[] arr={19,28,37,46,50,19,19};
// 0 1 2 3 4 5 6
System.out.println("请输入您要查找的值");
int[] result = getIndex(num, arr);//这里必须得是实参,除非用Scannner
if(result.length==0){
System.out.println("您要查找的元素,在数组中不存在");
}else {
for (int i = 0; i < result.length; i++) {
System.out.println(result[i]);
}
}
}
public static int[] getIndex(int num,int[] arr) {
//统计出来num的个数
int count = 0;
for (int i = 0; i < arr.length; i++) {
if (arr[i] == num) {
count++;
}
}
//根据统计出来的个数来创建一个数组,用于接受相同的元素
int[] result = new int[count];
int index = 0;
//查找元素在数组中的索引,并将其导入数组中
for (int i = 0; i < arr.length; i++) {
if (arr[i] == num) {
result[index] = i;
index++;//!
}
}//将带有结果的数组返回
return result;
}
1.1.49 需求:数组反转
需求:
已知一个数组arr={11,22,33,44,55};用程序实现把数组中的元素值交换
交往后的宿主arr={55,44,33,22,11};并在控制台输出交换后的数组元素
思路:
1.确定好谁跟谁换
第一个和倒数第一个:arr[0] arr[arr.length-1-0]
第二个和倒数第二个:arr[1] arr[arr.length-1-1]
第三个和倒数第三个:arr[2] arr[arr.length-1-2]arr[i] arr[arr.length-1-i]
public static void main(String[] args) { int[] arr={11,22,33,44,55}; reverseArray2(arr); for (int i = 0; i < arr.length; i++) { System.out.println(arr[i]); } } private static void reverseArray1(int[] arr) { for (int i = 0; i < arr.length/2; i++) { int temp=0; temp= arr[i]; arr[i]= arr[arr.length-1-i]; arr[arr.length-1-i]=temp; } } }
请想出第二种解办法:
在程序中设计两个指针,指针所指向的位置,交换
1.定义两个变量,模拟开始和结束指针
int start=0;
int end=arr.length-1;
2.交换
int temp=arr[0];
arr[0]=arr[5];
arr[5]=temp;
3.每一次交换完成,让两个指针向中间移动
start++;
end--;
数组反转的思路:
第一个元素和最后一个元素交换
第二个元素和倒数第二个元素交换
...
交换的条件:
start<end
private static void reverseArray2(int[] arr) {
for (int start = 0, end = arr.length-1; start < end; start++,end--) {
int temp=arr[start];
arr[start]=arr[end];
arr[end]=temp;
}
1.1.50 需求:输出评委平均分
需求:
在编程竞赛中,有6个评委为参数选手打分,分数为0~100的整数分
选手的最后得分为:去掉一个最高分和一个最低分后的4个评委的平均值
1.基本实现(不考虑分数校验)
2.校验键盘录入的分数是否是0~100之间
3.抽取方法
思路:
//1.键盘录入6个评委的打分
//2.求出6个数据的总和,然后从这6个数据中找到最大值和最小值,
//3.之后就用总分减去最大值和最小值
1.1.51 需求:校验验证码
需求:请从26个英文字母(大小写都包含),以及数字0~9中,随机产生一个5位的
字符验证码并打印在控制台
效果: uYqI,3r4Zj
分析:
得到随机验证码后要去做一个校验的行为
public static void main(String[] args) {
char[] chs = getContents();//获取内容Contents 内容
String checkCode = getCheckCode(chs);
//校验:即与用户输入的字符进行对比!
System.out.println("请输入验证码!");
Scanner sc=new Scanner(System.in);
System.out.println("产生的验证码为:"+checkCode);
/*if();无法比较因为你只能打印出来随机的字符串,此时还无法使用
必须的将打印出来的字符拼接成一个整体 去看StringDemo
字符串的比较还没学习到,暂时先做到这里*/
}
private static String getCheckCode(char[] chs) {
Random r=new Random();
String checkCode="";
char[] inputRandom=new char[5];
for (int i = 0; i < 5; i++) {
int index2=r.nextInt(chs.length);
checkCode+= chs[index2];
}
return checkCode;
}
private static char[] getContents() {
//定义一个数组满足题目要求
char[] chs=new char[26+26+10];//不是字符串
int index=0;
for (char i = 'a'; i<='z'; i++) {
chs[index]=i;
index++;
}
for (char i = 'A'; i <='Z'; i++) {
chs[index]=i;
index++;
}
for (char i = '0'; i <='9' ; i++) {
chs[index]=i;
index++;
}
System.out.println(chs);
return chs;
}
}
1.4 构造方法
1.1.51 构造方法(第7天)
构造方法 (构造器) :
创建对象的时候, 要执行的方法
格式:
1. 方法名与类名相同, 大小写也需要一致
2. 没有返回值类型, 连void都没有
3. 没有具体的返回值 (不能由return语句带回结果数据)构造方法的执行时机 :
在创建对象的时候, 被调用执行
每创建一次对象, 就会执行一次构造方法.构造方法的作用 :
1. 本质的作用 : 创建对象
2. 结合执行时机 : 可以创建对象的时候, 给对象中的数据初始化构造方法的注意事项 :
1. 一个类中, 没有编写构造方法, 系统将会提供一个 [默认的] [无参数] 的构造方法
2. 一个类中, 如果手动编写了构造方法, 系统将不会再提供那个默认的无参构造了
* 建议 : 编写类的时候, 无参构造, 带参构造, 全部手动给出3. 构造方法不允许手动调用
好处
1.更好的维护数据
2.使用者无需关心内部实现,只要知道如何使用即可
封装的设计规范同一个类当中,方法名相同,参数不同------->重载关系
//构造方法也是方法------>允许重载关系的出现
1.私有成员变量(目的:为了保证数据的安全性)
2.针对是有的成员变量,提供对应的setXXX和getXXX方法
set:设置
get:获取
封装的设计规范:合理隐藏,合理暴露
1.1.52需求:构造函数的练习
比较简单 跳过
1.1.53 就近原则
情况:成员变量和局部变量重名的情况,
Java使用的是就近原则问题:非要使用成员变量,怎么办?
解决:使用this关键字进行区分-------------------------------------------
this关键字的作用:
this可以调用本类成员(变量,方法)
this.本类成员变量
this.本类成员方法();this.的省略规则:
本类成员方法:没有前提条件,this.可以直接省略
本类成员变量:方法中没有出现重复的变量,this.才可以省略---------------------------------------
this介绍:代表当前类对类的引用(地址)
-谁来调用我,我就代表谁
!!(哪一个对象调用方法,方法中的this,就代表的就是哪一个对象(的地址).)stu1.print()---->this--->stu1的地址
stu2.喷淋头()---->this--->stu2的地址
1.1.54 java中的类
前提需知 : Java当中要想创建对象, 必须现有类的存在
类 : 一组相关属性和行为的集合, 将其看做为是对象的设计图.
对象 : 是根据设计图(类), 创建出来的实体类和对象的关系:
1) 依赖关系: 需要根据类, 创建对象
2) 数量关系: 根据一个类, 可以创建出多个对象类的组成:
类的本质 : 就是对事物进行的描述
举例1: 我之前有一个{学生}, 叫做<张三>, 今年<23岁>了, <180的身高>, 平时就喜欢(吃饭)和(学习)...
举例2: 前一阵买了一台<白色>的<海尔>{洗衣机}, 花了我<1999块钱>, 老心疼了, 但是(洗衣服)和(甩干)倒是挺方便...
属性(名词): 在代码中使用成员变量表示, 成员变量跟之前定义变量的格式一样, 只不过位置发生了改变, 类中方法外.行为(动词): 在代码中使用成员方法表示, 成员方法跟之前定义方法的格式一样, 只不过需要去掉 static 关键字
创建类对象进行使用
创建Student类的对象进行使用
1. 创建对象的格式
类名 对象名 = new 类名();2. 使用对象成员变量的格式
对象名.成员变量;3. 使用对象成员方法的格式
对象名.成员方法();----------------------------------------
细节:
1) 打印对象名, 可以看到对象的内存地址com.itheima.oop.Student@4eec7777
全类名 : 包名 + 类名2) 成员变量就算没有赋值, 也可以直接用, 使用的是对象的默认值
1.1.55 权限修饰符
权限修饰符 :
private : 同一个类中
(default) : 同一个类中, 同一个包中
protected : 同一个类中, 同一个包中, 不同包的子类
TODO: 继承
public : 任意位置访问
1.1.56 需求:展示电影内容
主类:
public class Test {
public static void main(String[] args){
Movie movie1=new Movie(1,"东八区的先生们","2022",2.1,"中国大陆","剧情 喜剧","夏睿","张翰 王晓晨");
Movie movie2 = new Movie(2, "上海堡垒", "2019", 2.9, "中国大陆", "爱情 战争 科幻", "滕华涛", "鹿晗 舒淇");
Movie movie3 = new Movie(3, "纯洁心灵·逐梦演艺圈", "2015", 2.2, "中国大陆", "剧情 喜剧", "毕志飞", "朱一文 李彦漫");
Movie[] movies={movie1,movie2,movie3};
//该如何将一个类中的数据,传递给另外一个类
MovieService movieService=new MovieService(movies);
movieService.start();
}
}
方法:
/**
* 启动电影信息管理系统
*/
public class MovieService {
private Movie[] movies;
private Scanner sc=new Scanner(System.in);
public MovieService(Movie[] movies) {//得到主类中的movies数据
this.movies=movies;
}
public void start() {//用于将系统启动起来
lo:
while (true) {//快捷键 选中需要的内容 ctrl + alt + T
System.out.println("-----------电影信息系统-------------");
System.out.println("请输入您的选择:");
System.out.println("1.查询全部电影信息");
System.out.println("2.根据id查询电影信息");
System.out.println("3.退出");
int choice=sc.nextInt();
switch(choice){
case 1:
queryMovieInfos();
break;
case 2:
System.out.println("请输入1或2或3进行选择");
queryMovieInfoById();
break;
case 3:
System.out.println("3.退出");
//System.exit(0); //终止正在运行的JVM虚拟机
break lo;
default:
System.out.println("您的输入有误!请检查!");
break;
}
}
}
/**
* 此方法根据电影编号,查询电影详细信息
*/
private void queryMovieInfoById() {
//1.键盘录入用户输入的编号
//Scanner sc=new Scanner(System.in);将其放在成员变量中,并私有化,没有必要暴露出去
System.out.println("请输入您要查询的电影编号");
int id= sc.nextInt();
//2.遍历数组,从数组中查询电影信息
for (int i = 0; i < movies.length; i++) {
Movie movie=movies[i];//按住ctrl 鼠标左键点一下这个Movie 进入这个类里面来
if(id== movie.getId()){
id=i;
//将找到的电影信息,打印在控制台
System.out.println(movie.getId() + "---" + movie.getTitle() + "---" + movie.getTime()
+ "---" + movie.getScore() + "---" + movie.getArea() + "---"
+ movie.getType() + "---" + movie.getDirector() + "---" + movie.getStarring());
return;
}
}
//代码要是到了这里,说明没找到
System.out.println("您输入的编号不存在,请重新输入!");
}
/**
* 展示出系统中全部的电影(名称,评分)
*
*/
private void queryMovieInfos() {
//1.遍历数组,取出每一个电影对象
for (int i = 0; i < movies.length; i++) {
Movie movie=movies[i];
//System.out.println(movie); 打印对象名,会看到内存地址
//2.通过电影对象,调用内部getXXX方法,获取信息并打印
System.out.println(movie.getTitle());
//这个得到的是地址System.out.println(movie);
//这个得到的是地址System.out.println(movies[i]);
}
}
}
总结:
1.得需要一个总方法(电影管理系统)也肯定需要Scanner方法
得需要一个启动电影管理系统,当系统一启动的话,我们就应该给他展示一个菜单
2.先搭建一个菜单吧!(其实就是一连串的打印语句)
然后switch语句来将用户输入的choice与菜单做匹配
3.发现只能运行一次,则我们应该加入循环!快捷键 ctrl alt T
并且 加入取别名功能 来更好的结束死循环
4.完善switch输出语句!
5.发现在switch case1 中需要添加一个方法 来进行
当用户输入1时 给人家打印电影目录
6.发现在switch case2 中需要添加一个方法 来进行
当用户输入2时 给人家打印这个电影的信息
1.5 String 类
1.1.57 String 类的特点
String类的特点:
1.java 程序中所有双引号字符串,都是String这个类的对象2.字符串一旦被创建,就不可更改,字符串内容不可更改
如果想要更改,只能使用新的对象,做替换3.String字符串虽然不可改变,都是可以被共享
字符串常量池:当我们使用双引号创建字符串对象时,
会检查常量池中是否存在该数据
不存在:创建
存在:复用
(jdk7版本之前:StringTable是在方法区中
(jdk7版本开始:StringTable是在堆内存中
public static void main(String[] args) {
String s="abc";//只有对象才用.调用var/toUpperCase...等许多方法
System.out.println(s.toUpperCase());
System.out.println("hellowold".toUpperCase());//只要是写了双引号字符串
// 他就已经是String字符串的对象了
s="def";
System.out.println(s);
Student stu=new Student("张三",23);
stu =new Student("李四",24);
System.out.println(stu.getName()+"---"+stu.getAge());
String s1="abc";
String s2="abc";
System.out.println(s1==s2);//比较的是地址 运行的结果是true
}
}
1.1.57 String类中常见的构造方法
public String() :创建有个空白的字符串,里面不含任何内容
public String(char[] chs):根据传入的字符数组,创建字符串对象
public String(String original):根据传入的字符串,来创建字符串对象注意:
双引号创建出的字符串和new出来的字符串区别:内存地址不一样
双引号的:在string table中
new的:堆内存中有自己独立的空间
public static void main(String[] args) {
//public String():创建一个空白字符串,里面不含任何内容
String s1=new String();
System.out.println(s1);
//public String(char[] chs):
char[] chs={'a','b','c'};
String s2=new String(chs);
System.out.println(s2);//abc
}
1.1.58 String 类中常见面试题
请问是false还是true:
答案:false
原因:
那下一题请问是false还是true:
答案为true
原因:由于java中存在常量优化机制:"a"+"b"+"c"会自动转化为"abc"
1.1.59 String类的比较
String类中用于比较的方法 :
将此字符串与指定的对象比较
public boolean equals(Object anObject)
将此 String 与另一个 String 比较,不考虑大小写
public boolean equalsIgnoreCase(String anotherString)
1.1.60 String类的遍历方法
第一种方法:
/**
* 字符串的第一种遍历方式
*/
private static void print1() {//什么时候加static?
//如果你的方法与主方法是平级的,那么就带有static
//反之,都不加!
String s ="itheima";
char[] chars = s.toCharArray();//将字符串转换为字符
for (int i = 0; i < chars.length; i++) {//数组的length是一个属性是没有括号的
System.out.println(chars[i]);
}
}
推荐第二种方法:
/**
*字符串的第二种遍历方式
*/
public static void main(String[] args) {
print1();
String s ="itheima";
for (int i = 0; i <s.length(); i++) {//这里是带括号的 方法
//i=0 1 2 3 4 5 6
char c=s.charAt(i);
System.out.println(c);//itheima
}
1.1.61 String类的截取方法
String类的截取方法 :
根据传入的索引开始做截取, 截取到字符串的末尾
public String substring(int beginIndex) :
根据传入的开始和结束索引, 对字符串做截取
- 包含头, 不包含尾 [ )
public String substring(int beginIndex, int endIndex) :注意: 截取出来的内容, 是作为新的字符串返回, 别忘记找变量接收!!!
1.1.62 String类的替换方法
String类的替换方法 :
public String replace(CharSequence target,CharSequence replacement) :
参数1 : 旧值
参数2 : 新值
1.1.63 String类的切割
String类的切割方法 :
根据传入的字符串作为规则, 切割当前字符串
public String[] split(String regex).是一个通配符 指的是任意的字符(会切碎糊了)
可以前面加 \\建议: 先正常指定切割规则, 后来发现没有得到自己要的效果,
就可以尝试在规则前面, 加入 \\
"abababafba"
.toCharArray()方法 可以拆分字符串
char[ ] charArray=info.toCharArray();
public static void main(String[] args) {
String s = "192+168+1+1";
String[] sArr = s.split("\\+");
for (int i = 0; i < sArr.length; i++) {
System.out.println(sArr[i]);
}
}
}// 192
// 168
// 1
// 1
1.1.64 StringBuilderDemo
有字符串拼接操作就得想到StringBuilder
StringBuilder的作用 : 提高字符串的操作效率
学习目的:
1. StringBuilder的特点
2. StringBuilder的构造方法
3. StringBuilder常用成员方法
4. 练习
5. StringBuilder提高效率
主方法中使用StringBuilder拼接一万个字符串用时10秒
method()方法中String普通字符串拼接一万个用时2004秒 StringBuilder提高效率 完胜
public static void main(String[] args) {
long start = System.currentTimeMillis();//start开始节点
StringBuilder sb = new StringBuilder();
for(int i = 1; i <= 100000; i++){
sb.append(i);
}
System.out.println(sb);
long end = System.currentTimeMillis();//结束节点 end
System.out.println(end - start);// 10
//method();
}
private static void method() {
// 获取1970年1月1日0时0分0秒到现在所经历过的毫秒值 (1秒 = 1000毫秒)
long start = System.currentTimeMillis();
String s = "";
for(int i = 1; i <= 100000; i++){
s += i;
}
System.out.println(s);
long end = System.currentTimeMillis();
System.out.println(end - start); // 2804
}
}
1.1.65 String类中常见的构造方法
String类常见构造方法 :
public String() : 创建一个空白字符串, 里面不含任何内容
public String(char[] chs) : 根据传入的字符数组, 创建字符串对象
public String(String original) : 根据传入的字符串, 来创建字符串对象-----------------------------------------------------------------
1. 打印对象名, 会看到对象的内存地址, 这里打印字符串对象, 为什么没有看到地址值
回答: 暂不解释
TODO: 面向对象(继承), 方法重写, Object类, toString方法2. 这三个构造方法, 创建字符串对象, 都没有双引号直接创建来的方便.
String s = "abc";
-----------------------------------------------------------------
字符串对象, 两种创建方式的区别
1. 双引号直接创建
2. 通过构造方法创建
打印对象名, 会看到对象的内存地址, 这里打印字符串对象, 为什么没有看到地址值?
在Java中,打印对象的默认行为是调用对象的
toString()
方法。对于大多数对象,包括字符串对象,toString()
方法的默认实现会打印对象的内存地址(即对象的哈希码),但字符串对象在toString()
方法中被特别处理。详细说明:
默认的
toString()
实现:
- 对于大多数Java对象,
toString()
方法的默认实现是输出对象的类名和对象的哈希码,例如:public String toString() { return getClass().getName() + "@" + Integer.toHexString(hashCode()); }
- 这个方法的输出通常看起来像
ClassName@HashCode
,其中ClassName
是对象的类名,HashCode
是对象的哈希码。字符串对象的
toString()
实现:
- 对于
String
对象,toString()
方法被重写以返回字符串的内容。也就是说,toString()
返回的是字符串对象内部保存的字符序列,而不是内存地址或哈希码。因此,打印字符串对象时,你看到的是字符串的实际内容。示例:
String str = new String("Hello");
System.out.println(str); // 输出: Hello System.out.println(str.toString()); // 输出: Hello
在这里,
str
是一个字符串对象,System.out.println(str)
直接输出了字符串的内容“Hello”。由于String
类重写了toString()
方法,返回的是字符串的实际值而不是内存地址。总结
字符串对象的
toString()
方法返回字符串本身,而不是对象的内存地址或哈希码。这是因为String
类重写了toString()
方法,提供了更有用的输出,直接显示字符串内容。这种行为与其他大多数对象不同,后者通常会显示内存地址或哈希码。
在Java中,new String("someString")
会在堆内存中创建一个新的 String
对象。至于这个对象会存储在哪里,涉及到两种情况:
-
堆内存中的普通对象:
- 使用
new String("someString")
创建的字符串对象会存储在堆内存中,但它与字符串常量池(String Pool)不同。
- 使用
-
字符串常量池:
- 当你使用字符串字面量(例如
"someString"
)时,这个字符串会存储在字符串常量池中。这是一个特殊的内存区域,用于缓存不可变的字符串字面量,以节省内存和提高性能。
- 当你使用字符串字面量(例如
关键点:
-
字符串常量池:
String
字面量会被自动放入字符串常量池。例如,"someString"
会放在池中,以便重复使用。
-
新字符串对象:
new String("someString")
创建的对象是在堆内存中分配的,独立于字符串常量池。它实际上是一个String
实例,它会持有对字符串常量池中对应常量的引用,但不会直接放入常量池中。
总结
new String("someString")
创建的对象会在堆内存中分配,属于普通的对象实例,而不是字符串常量池中的内容。字符串常量池主要用于优化字符串字面量的存储和重用。
1.1.66 Scanner中的next和nextLine
Scanner键盘录入字符串
String next():遇到了空格,或者tab键就不再录入了
String nextLine():以回车作为录入的结束标志弊端:
1.next():数据可能录入不完整
2.nextLine():之前调用过nextInt(),nextDouble(),nextFloat()...
如果再nextLine()方法,就不干活了
解决方法:不用解决
Scanner:采集用户信息(只在学习过程用得到) Interger.parse(sc.nextLine())将数字字符串转换为数字 这个代替nextInt() 从而解决 nextLine()与nextInt()冲突的问题
目前的使用方案:
需求如果要键盘录入字符串
如果所有的数据,全部都是字符串,直接nextLine();
举例:
键盘录入用户名,键盘录入用户密码
如果数据除了字符串,还有其他类型,需要调用next()方法
举例:
键盘录入用户名,键盘录入用户年龄,用户身高
public static void main(String[] args) {
Scanner sc=new Scanner(System.in);
System.out.println("请输入一个整数");23+回车
int age=sc.nextInt();
System.out.println(age);
System.out.println("请输入字符串");
String name=sc.nextLine();//这里 识别到回车 作为结束录入的标志
System.out.println(name);
}
}
/*请输入一个整数
23
23
请输入字符串
进程已结束,退出代码0
演示:
1.next():数据可能录入不完整
2.nextLine():之前调用过nextInt(),nextDouble(),nextFloat()...
如果再nextLine()方法,就不干活了
public static void main(String[] args) {
Scanner sc=new Scanner(System.in);
System.out.println("请输入一个整数");// 23 +回车
int age=sc.nextInt();
String s = sc.nextLine();//这一步是执行不到的,因为 前面有nextInt()
System.out.println(s);//这步执行不到
System.out.println(age);
System.out.println("请输入字符串");
String name=sc.next();//如果输入的字符有空格,tab 那么空格后的数据是无法打印的 数据遗失 录入不完整
System.out.println(name);
}
}
请输入一个整数
23
23
请输入字符串
23 23
23
1.1.67 StringBuilder的特点
StringBuilder的介绍 :
1. 一个可变的字符序列
2. StringBuilder是字符串缓冲区, 将其理解是容器, 这个容器可以
存储任意数据类型, 但是只要进入到这个容器, 全部变成字符串.
全部变成字符串.全部变成字符串.全部变成字符串.全部变成字符串.StringBuilder的构造方法 :
public StringBuilder() : 创建一个空白的字符串缓冲区(容器),
其初始容量为16个字符(超过了16个会自动扩容的)public StringBuilder(String str) : 创建一个字符串缓冲区(容器),
容器在创建好之后, 就会带有参数的内容(带参构造与不带参构造 类似于 数组的动态初始化, 静态初始化)
1.1.68 StringBuffer
StringBuilder常用成员方法 :
1. public StringBuilder append(任意类型) : 添加数据, 并返回对象自己
2. public StringBuilder reverse() : 将缓冲区中的内容, 进行反转
3. public int length() : 返回长度
4. public String toString() : 将缓冲区的内容, 以String字符串类型返回
1.1.69 需求:判断是否为对称字符串
需求:键盘接受一个字符串,程序判断出该字符串是否是对称字符串
(回文字符串),并在控制台打印是或不是
对称字符串:123321 ,111
非对称字符串:123123思路:对拿到的字符串进行反转(reserve),若跟原数据相同,则判定为回文字符串
public static void main(String[] args) {
//1.首先会有键盘录入
Scanner sc=new Scanner(System.in);
System.out.println("请输入一个对称字符串");
String content=sc.nextLine();
//将String转换为StringBuilder,为了调用内部反转的方法
StringBuilder sb=new StringBuilder(content);
String reverse = sb.reverse().toString();
System.out.println("原来的数据:"+content);
System.out.println("现在的数据:"+reverse);
//判断反转后的内容,和原数据是否相同
//content: String类型
//sb:StringBuilder类型 将sb转换为String类型才能比较
if(reverse.equals(content)){
System.out.println("该字符串为对称字符串");
}else {
System.out.println("该字符串不是对称字符串");
}
}
1.1.69 需求:字符串拼接输出
需求:定义一个方法,把int数组中的数据按照指定的格式拼接成一个字符串
返回,调用该方法并在控制台输出结果例如:
数组为int[] arr={1,2,3};
执行方法后的输出结果为:[1, 2, 3]
//public String toString() : 将缓冲区的内容, 以String字符串类型返回
public class StringBuilderTest2 {
/*
需求:定义一个方法,把int数组中的数据按照指定的格式拼接成一个字符串
返回,调用该方法并在控制台输出结果
例如:
数组为int[] arr={1,2,3};
执行方法后的输出结果为:[1, 2, 3]
*/
public static void main(String[] args) {
int[] arr={1,2,3};
arrToString(arr);
}
//题目要求有返回,则应该想到得来个方法
//2:two:to(速写不推荐)
//4:four:for
public static String arrToString(int[] arr){//形参arr传递进来
//有(大量(5次)拼接操作,联想到StringBuilder方法(大幅度提高效率)
//先搭一个架子 注意架子是在new StringBuilder()括号中搭建
StringBuilder sb=new StringBuilder("[");
//架子ok之后,就要遍历数组
for (int i = 0; i < arr.length-1; i++) {
sb.append(arr[i]+", ");
}
//System.out.println(sb);//发现最后一个元素得特殊处理
//对最后一个元素进行特殊处理
System.out.println(sb.append(arr[arr.length-1]+"]"));
return sb.toString();
}
}
1.1.70 需求:模拟用户登录
需求:模拟用户登录,一共三次机会,登录之后要给出相应的提示
分析:
1.定义两个变量,模拟已经存在的用户名和密码2.键盘录入用户输入的用户名和密码
3.对比
1.1.71 需求:统计字符出现次数
需求:
键盘录入一个字符串,统计该字符串中大写字母字符,小写字母字符,数字字符出现的次数
(不考虑其他字符)例如 :aAb3&c2B*4CD1
小写字母:3个
大写字母:4个
数字字母:4个
提示:关键是toCharArray()方法
1.1.71 需求:接收验证码
需求:
以字符串的形式从键盘接收一个手机号,将中间四位号码屏蔽
最终效果为:156****1234
public static void main(String[] args) {
//接受!
Scanner sc=new Scanner(System.in);
System.out.println("请输入您的手机号");
String phoneNumber= sc.nextLine();
String result1 = phoneNumber.substring(0, 3);
String result2 = phoneNumber.substring(7);
System.out.println("屏蔽后为:"+result1+"****"+result2);
}
}
1.1.72 需求:TMD取代
需求:
键盘录入一个字符串,如果字符串中包含(TMD),则使用***替换
public class StringTest4 {
public static void main(String[] args) {
Scanner sc=new Scanner(System.in);
System.out.println("请输入骂人的话,请包含TMD:");
String zhiFu = sc.next();//也可以用已有的zhiFu做接收
String chars= zhiFu.replace("TMD","***");
System.out.println(chars);
}
}
1.1.73 积累的String类方法
1.toCharArray方法
在字符串的遍历方法当中,将字符串转化为字符序列
2.contains方法
String str=file.getname();
str.contains(" XXX"); 判断字符串中是否含有XXX信息
3.String
String s=new String (chs,0,len);将传入的chs字符数组从索引0到索引len截取下来赋值给s
基础篇完结