欢迎光临散文网 会员登陆 & 注册

【零基础 快速学Java】韩顺平 零基础30天学会Java

2022-07-13 16:17 作者:MapleCupTea  | 我要投稿

JAVA基础跟课笔记



JAVA转义字符篇

\t 一个制表位(即一个固定宽度的空格)

1.使用位置:文本处

2.使用效果:

原文本:北京天津上海

修改:北京\t天津\t上海

结果:北京 天津 上海

3.说明:由于是固定宽度,可以实现对齐效果

4 补充:可以多次使用\t来加宽(\t\t)

下面类似


\n 换行符

1.注意:不能直接用回车来实现换行

2.使用位置:文本处

3.使用效果:

原文本:jacksmithmary

修改:jack\nsmith\nmary

结果:jack

smith

mary

补充:在使用System.out.println("")时,其中ln表示输出后换行,不加ln就不会进行换行


\\ 单独输出“ \ "

1.说明:第一个 \ 表示转义命令

第二个 \ 表示要转义的内容(即 \ )

2.补充:要输出两个 \ 时打: \\\\

其它以此类推


\" 输出 ”

\' 输出 ‘

1.说明:由于System.out.println("")自带一对“

若文本再有“会导致系统无法理解文本范围而判断为非法表达式


\r 表示回车

1.注意:

不同于我们理解的回车(即不是换

行),而是将鼠标光标回到当前行文

本第一个字。这时直接输入文字会替

换原来文字

2.使用效果:

原文本:韩顺平教育北京

修改:韩顺平教育\r北京

结果:北京平教育

3.补充: \r\n可以实现换行效果


PS:要对文字进行如上几个变换,一般先将所有文本写完,再来进行转义字符的加入



JAVA注释篇【做一个负责的人】

一 为什么要养成写注释的习惯

一曰可以帮助你理清思路,哪怕隔很长时间再回来看,也能快速掌握代码内容与项目目标。二曰可以帮助接管你程序的人也能懂你的代码思路,是一种高情商的表现,能防止你被人追杀。


二 三种注释

单行注释

1.格式://注释文字

2.说明:只能在一行内实现注释,换行就失去注释功能

多行注释

1.格式:/* 注释文字*/

2.说明:可以在注释范围内任意换行

3.注意:不可以嵌套多行注释


PS:注释存在编码,若注释有中文要用GBK

注释不会被JVM执行任何命令


文档注释

1.说明:注释内容可以被JDK提供的工具javadoc解析,生成一套以网页文件形式体现的说明文档

2.基本格式: /**

* javadoc标签1

* javadoc标签2

.......

*/

3.如何生成对应的说明文档:

首先,打开控制台

其次,输入javadoc -d 具体文件夹名(包

含路径) -javadoc标签1 -javadoc标签2 ..... 你所编译的java文件

最后,回车


4.如何看生成的说明文档

首先,打开生成的说明文档所在的文件夹

其次,找到后缀为html的文件

最后,右键找打开方式,点浏览器即可


5 .常用的javadoc标签



变量篇

一 为何需要变量

放眼你我所处的世界,若尝试用变量(顾名思义,即能发生变化的量)的概念去描述这个世界,你便发现几乎万物都脱胎于它。如人的呼吸,昼夜的变化,四季的轮转,行星的舞步乃至宇宙的气息,都能用可“变”的“量”来描述。

程序亦是如此。韩老师言:“一个程序就是一个世界。”使用变量既可以实现程序的生命,又可以切实影响到现实世界的变量。

变量很抽象,却又很实在。


变量是程序的基本组成单位



二 变量的三个基本要素

1.数据类型

2.变量名称

3.变量的值

例如(定义一个变量)

int a = 1

int表示数据类型为整型,a表示变量名称,=表示赋值,1表示变量的值

整体含义即 将1赋值给整型变量a


三 变量是如何体现在计算机上的

提要:学会将变量代码与计算机的工作原理结合起来,更容易理解与学习变量

例如:int a = 1

当执行时,计算机的内存部分会分配一定的空间并在其中放置变量的初始值 1 ,之后内存会定义一个变量a,并由其作为主体在内存中指向该区域,从而实现连接变量与值的目的(本质上没有赋值,a还是a,只是将a与该区域联系并统一起来,这样计算机看见a,不仅知道它是变量,而且可以调动它所连接的区域内的值,对a进行替换。这样运算a 其实对计算机来说,即运算替换a的数值。更通俗的来讲,就是中学常用的换元法,帮助简化式子)

a = 89

当执行时,计算机内存会将已经与相应区域联系好的变量a(说明要先定义一个变量)去改变区域内原本的数为89


System.out.println(a)

结合上面理解,计算机看见a,就会去找其联系的区域内的数值,最终用数值替换a,再将替换的输出到控制台上


PS:单独只有一个变量的输出不需要“”


诚如韩老师讲的变量的概念:变量相当与内存中一个数据存储空间的表示,你可以把变量看作是一个房间的门牌号,通过门牌号我们就可以找到房间,而通过变量名可以访问到变量(值)(这里即老师之前说的变量是地址)


补充:int a = 1 其实是两个指令

即 定义变量名与数据类型:int a

赋值变量:a = 1


四 变量使用的注意事项

说明:

1. 对第三点程序执行有顺序,可以参考高中数学算法一章

2. 对于第四点,隐含一个知识: 数据类型不可以混用

3 . 对于第五点的作用域,见后面详细内容。(大致就是在一定的范围里如在同一个类里,不得有两个及以上的相同名的变量)


五 JAVA数据类型

(一) 分类

说明:byte:字节 占一个字节

short:短整型 占两个字节

int:整数 占四个字节

long:长整型 占八个字节

float:单精度 占四个字节

double:双精度 占八个字节

通过多个分类,节省内存空间

String是引用数据类型,属于类


(二) 整数类型

用于储存整数

说明:当所要储存的值满足某些类型的范围时,不同的类型对相同的值有不同的占用空间。例如:10这个值满足以上四种类型的范围,用byte的类型,这个值只占1个字节。而用long的类型,同样是10,则要占用8个字节。可以理解为同一个人在不同面积的房间里


(三) 整型细节

1.Java的各个整数类型都是固定的,在不同操作系统都是一样的


2.整型常量(即给定的具体值)默认为int型。在使用long型时,常量的后面需要加字母L(不分大小写)

注意:在使用其它类型时,不得在其后加L

否则从long型转到其它较小的类型时可能会存在数据的丢失(理解为房间太小,东西太多,不得不丢掉一些东西)

在使用long型时,不加L且数超过int的范围也是不可以的。尽管相当于把int的数放在更大空间的long中,但数值本身超过了默认数值类型int的可储存范围,导致数值无法录入,没法录入,何谈转到其它空间?由此推知,不加L且数未超过int的范围是可以的。此时就是小房间到大房间的转换了。


但对于其它的short,byte时,就只能在相应范围类输入值了

原因:计算机会先判断数是否在它们各自的范围内,如果是就可以。如果不能先判断数的范围(比如赋值一个变量),此时计算机会判断类型的大小,大转小不行,小转大可以,注意这里只看类型,而不看数的大小(详见下文的自动类型转换

例如:

(1)byte a = 10; 编译成功

(2)int b = 1;

byte c = b ; 编译失败


3.整型使用时,一般遵循使用较小空间的整数类型的原则(节省空间原则)


4.bit是计算机中最小的存储单位。

1 byte = 8 bit

bit存放 0 1 ,是用来二进制的

由此可以用来解释上文为什么相同值在不同类型所占的空间不同。

例如给定一个整型常量3

在byte中表现为00000011

在short中表现为0000000000000011

在二进制的算法上,两者都表示数值3,但显然,在形式上,上面的更简练。


(四) 浮点数类型

用于存储小数

说明:浮点数在计算机中存放形式为:浮点数=符号位 + 指数位 + 尾数位(这些位可以理解为上面说的bit,都是计算机通过二进制来还原小数的一种方式,利用这几个位,实现还原)其中尾数位容易丢失数据,造成精度的损失,故而称小数都是近似值。


(五)浮点数细节

1.Java的各个浮点数类型都是固定的,在不同操作系统都是一样的


2.浮点数常量默认为double型。在使用float型时,常量的后面需要加字母F(不分大小写) 其原因同讲整数细节时一样


3.两种表示形式:

(1)十进制数形式:5.12 0.23 等常规形式以及个位为0时另一种表现形式 .154

(2)科学计数法:5.12e2[即5.12*10^2](e不区分大小写)但由于是浮点类型,最终答案为512.0而不是512


4.通常,应使用double型,其精度更高(高精度原则)

在输出时,float型会出现小数不能完全保留情况,且只是粗暴地删去而非四舍五入。

例如: 在float型储存一个2.1234567851,结果在输出时,只有2.1234567


5.浮点数使用陷阱

不要对运算结果(不是赋值的)是小数的进行比较

原因:计算机运算不同于人,在进行8.1/3时,对人来讲,8.1就是8.1。而对计算机来讲,由于8.1是小数,则会将其理解为浮点数并带上精度。由于带上了精度,在计算机上可能会表现为8.100001...则在计算时,会计算出2.6999999997这样违反常识的值。故在比较2.7与8.1/3时,计算机不能给出“相等”的答案

非要比较,那怎样避免?

答:利用相比较的两数差值,根据差值的大小来判断

代码如下:

对math.abs()的补充:

这里涉及JAVA API文档

API(应用程序编程接口)其实是JAVA设计者给程序员提供的编程上的 (用于描述编程对象信息的模子,就好比是B站登录时,手机号栏与密码栏,而对象信息就是你登录的手机号与密码)方法(顾名思义,是用于解决问题的,而要解决这些问题,在程序中是通过一组代码语句来实现的。故方法是语句的集合,让它们一起执行一个功能)

API文档用于告诉开发者如何使用这些类,以及这些类里包含的方法


这里可以查询到API文档:

https://www.matools.com


如何查找到自己想用的类与方法?

首先应当了解API文档里是怎样组织的

之后由此图来查找

例如:查找ArrayList有哪些方法

法一

第一步:明白了该类在哪个包里(在java.util)

第二步:进入API文档,在左栏上部找到该包

第三步:找到并点击后,看左栏下部找到“类”

找到所要的类,并点击

第四步:右边出现信息,查找“方法”并浏览即可


法二(不知道类在哪个包的)

第一步:点工具栏“显示”

第二步:在“索引”中查找即可


(六) 字符类型char

用于存储单个字符(多个字符用字符串String)

字符包括:字母,汉字,数字,转义字符

注意:字符类型可以直接存放一个数字,故可以写:char c = 97; 没有使用英文单引号而其它的必须使用英文单引号。


本质上字符,在计算机中都会转换成数字代号,即编码,且这个编码都是整数



由于未加单引号,97在计算机中,会被理解为编码,那么接下来,计算机会通过unicode编码表码(一个将所有字符用数字编号的表)转换成所对应的字符。在unicode码中,97对应的字符是字母a,故最终输出其实为 a。若想输出数字本身,则需要加单引号’且为一个数字



unicode码查询:

https://tool.chinaz.com/Tools/Unicode.aspx


(七)字符型细节

说明:

(1)用“”的其实为字符串类型,这里使用会出现不兼容问题

(2)转义字符合起来算作一个字符

(3)对第3点,通过加上(int)实现将字符转换成对应的数字

char c = 'a';

System.out.println((int)c);

最终输出的是97,而非a

(4)对第5点,例子如下

System.out.println('a' + 10);

输出107(这里说明加上单引号就表示为char类了。而整体未加“”说明不是字符串,是可以进行计算的数字或变量)

或者

char c = 'a';

System.out.println(c + 10);

输出107(基本的变量运算)

或者

char c = 'a' + 1;

System.out.println(c);

输出字符 b(不同于上面两个的原因,是因为这里的运算是在变量本身进行的,而变量本身是char类,运算后的数字将会转换为相应的字符)


(八) 常用编码

除了上文的unicode码,还有许多其它编码


1.ASCII码:历史上最早的编码。由美国制定的,实现了将英语字符用数字编号的功能(数字可以转换为二进制形式,故又可以称二进制位)。该码用一个字节表示,一共编码了128个字符(实际上一个字节可以表示256个字符)

2.Unicode码:该码用两个字节表示,实现了字母与汉字的编码统一(但缺点就是容易浪费空间)。该码是第二个编码,是适应中国用户而编创的,可以认为它是ASCII码的拓展。实际上,该码将世界上所有常用符号都纳入其中了。因此,使用该码一般不会出现乱码

3.utf-8码:该码其实是Unicode码的改进,字母由于数量少,字节数要求少,故字母使用1个字节。而汉字数量多,字节数要求多,故汉字使用3个字节(表示更多的汉字)。从而节约了内存空间

4.gbk码:该码可谓是为汉字而生,在utf-8码的基础上,再次压缩,汉字仅占两个字节,且范围更加广泛(但两个字节并没有完全囊括所有汉字)

5.gb2312码:也是为汉字而生,但表示的汉字比较少,较为少用

6.big5码:该码实现了对繁体汉字编码,方便了港澳台地区的使用(但只支持繁体字的存储)



(九) 布尔类型

只能用于存储 真[true] 假[false]



六 基本数据类型转换

(一) 自动类型转换

例如:

int a = ' c ' ;

该语句中,变量a被定义为整型int,但赋值了一个字符型char。由于自动类型转换机制的存在,字符型 c字母根据编码表转换为了整型,故编译时没有报错

PS:转换可以跨越,不一定要相邻转换

例如:

double d = 80

变量d是双精度,赋的值80是整型。由于符合精度大小排序,尽管之间间隔了long型,float型,但仍一步到位,在计算机中变量d的存储其实为80.0


(二) 自动类型转换注意与细节

说明:

1.第一点与第六点本质相同,可以合在一起讲。其中这里容量最大的类型不光要看定义变量时的数据类型,还要看数值在默认状态下的数据类型。例如1.1数值出现时,默认为double类型,10数值出现时,默认为int


2.在进行计算时,一定要牢记自动类型转换的变换链,不得出现大转小情况

例如: float a = 10 + 1.1 该表达式错误的原因是因为变量a是单精度类型,而10 + 1.1根据第一点与第六点,这里的运算结果是双精度double类型,根据这条赋值语句,出现了大类型转小类型的情况,故表达式错误

改: double a = 10 + 1.1 或 float a = 10 + 1.1F


3.对三四点,可以类比上面讲的内容


(三) 强制类型转换

用于逆自动类型转换,往往是大转小

注意:强制转换,是可能造成数据部分丢失,其类型往往表现为精度缺失与数据溢出

强制转换的方法:在要强制转换的数值或变量前加 (数据类型)

例如: int a = (int)1.9;

或: int b = 100;

byte c = (byte) b;


(四) 强制数据类型转换的细节说明


说明:

1.对第二点可以理解为就近原则与整体思想。就近原则即强制转换的数值是与强转代码最近的那一个。

例如: int a = (int)10 + 1.1 该式子报错的原因是因为就近原则,强制转换的是10而不是10 + 1.1 ,而10 + 1.1的结果是double类型,出现了大转小的情况。整体思想是指的强转代码最近的哪一个可以使用()来整体化,从而实现整体的强转。由此上面的式子可以改为int a = (int)(10 + 1.1)


(五) 基本数据类型转字符串String

语法:在基本类型的值或变量后加上 + “”即可

例如: int a = 100;

String b = a + "" ;

PS:1.敲击空格键来输出 空 也是一种字符

2.字符串使用双引号


(六) String类型转基本类型

语法:

通过在 基本类型包装类 里调用一个叫parseXX的方法 的语句

类型:

1.转整型:Integer.parseInt("字符串")

2.转双精度:Double.parseDouble("")

3.转单精度:Float.parseFloat("")

4.转短整型:Short.parseShort("")

5.转长整型:Long.parseLong("")

6.转布尔型:Boolean.parseBoolean("")

7.转字节型:Byte.parseByte("")

8.转字符型:“字符串”.charAt(数字N)

注意:字符串转字符其实只取字符串的第N+1个字符


(七) 有关String类型转换的细节




运算符篇

一 什么是运算符

运算符是一种特殊的符号,可以用于数据的运算、赋值、比较等


二 运算符类型


(一) 算术运算符

定义:用于运算数值的符号

类型:

说明:

1.加号与减号在不同含义中有不同的语法,要注意区别


2.在计算时,仍然要满足上文讲的自动类型转换原则。例如在计算 10 / 4时,由于最高精度是int,故计算结果用int表示,故答案是2而不是2.5。要想得到2.5,则需要在计算时用上double类型的数值


3.模%的使用运用了数学上取余数的公式

a % b = a - [a/b] * b

[]表示取整,且a/b中a若是小数,则会强转为int型


4.++与-- 是在原来的数上加或减1。

如果只是单独的++或--,那放前放后,结果都是一样的

例如: int a = 10; int a = 10;

a ++ ; //结果为11 ++ a ; //结果为11

如果是用于表达式,则在前是先自增后运行其它(赋值,比较等),在后则是先运行其它再自增

例如: int b = 8;

int c = ++b //等价于 b=b+1;c=b;

int d = b++ //等价于 d=b;b=b+1;


补充:运算中的疑难问题

(1) int i = 1

i = i++

计算机对此的处理顺序为:

第一步:将变量 i 赋值给计算机给的临时变量temp,即temp = i

第二步:i 进行自加,即 i = i + 1

第三步:将temp变量赋给变量 i = temp

故结果仍然为 1 (自加了个寂寞)

(2) int i = 1

i = ++i

计算机对此的处理顺序为:

第一步:i 进行自加

第二步:将变量 i 赋值给临时变量 temp

第三步:将temp 赋值回 i

故结果为 2

(3) 设计程序三部曲:

序章:了明目标需求

主奏:根据需求找思路(怎么定变量,用什么代码,用什么公式)

尾声:写代码,跑代码


(二)关系运算符

比较数值,输出boolean型。由于其特性,往往用于if结构的条件中或循环结构的条件中


类型:

说明:

1.一个 = 表示赋值。只有两个 = 时才表示相等

2.instanceof将会在后面讲类时会具体说明

3.字符串的比较不可用 == ,而是用【要判断的字符串】.equals("要比较的字符串 ")

或者,将两者调换位置【要比较的字符串】.equals("要判断的字符串 ")。其中后者可以避免要判断的字符串为空而报错


(三) 逻辑运算符

用于连接多个条件(即多个关系表达式),和关系运算符一样,运算结果仍为boolean值


类型:

说明:

  1. a和b是两个可含变量的条件语句
  2. &或&&可以理解为是否全为真(即高中的∩);|或||可以理解为是否有真(即高中的∪);!可以理解为高中的非;^可以理解为是否不同,如果相同则取反
  3. 相关名称:&……逻辑与

|……逻辑或

^……逻辑异或

&&……短路与

||……短路或

!……取反

4.短路与逻辑的区别:短路不同于平常理解的短路,而是字面意思上的“短”。计算机在执行时,若在判断第一个条件时就已经能够得出最终结果时,就会直接跳过第二个条件的判断,从而实现缩短执行,使得代码运行更快。而逻辑的则是两个都要进行判断,相对来说代码运行较慢。当然,当第一个不能得出结果,则仍然要判断第二个

例如:

由于使用了短路与,在第一个条件不成立时就已经可以得到false的的答案,故不再执行对第二变量的判断与运算。故结果为:不输出ok300,其中a=4,b仍然为9

(四) 赋值运算符

用于将数值(包括运算后的)赋给指定变量


类型与含义:

细节与特点:

说明:对第四点,对b += 2 若是理解为b = b + 2时,则会由于b是byte类型,而b + 2 的结果是int类型而报错。然而并非如此,计算机对此的真正理解为 b = (byte) (b + 2),故不会报错。同理b ++也有如此转化


(五) 三元运算符

可以理解为简化的if语句

语法:条件表达式 ?表达式1 :表达式2;

说明:当条件表达式为true,则执行表达式1,反之执行表达式2。由于往往涉及变量,则需要充分掌握变量中的易错点(数据的转化,数据类型等)。三元运算符一般要配合其它语句一起使用。在理解语句时,往往先判断,再把判断出的表达式保留,其它的忽略,重新组合出一个整体的表达式

例如: int a = 10;

int b = 5;

int c = a > b ? a : b ;

在理解时,发现a>b成立,则只看表达式1,忽略其它,则重新组合的为 int c = a;


补充:

1.运算符优先级

说明:

(1)上一行运算符总先于下一行,大致概括为

(2)单目运算是对一个数或一个变量进行运算,例如++ 。而赋值运算即表中最后一类

(3) 逗号的使用:例如int a = 1 , b = 2 ;实现了前后化整体的作用

(4)>> << >>>是位移运算符(也称移位运算符)会在之后 位运算符 章节讲解


2.标识符的规则与规范

(1)概念:即对各种变量、方法和类等命名时用的字符序列。例如 int a = 10 中 a 就是标识符,对变量命名

(2)规则(必须遵守):

说明:所谓关键字,其实就是java中已经存在的代码名称,具有特殊用途的字符串,比如class、public等。而保留字是java中将会加入的代码名称。而“包含”其实就是在一串字符中可以出现这些词

(3)规范(更加专业):


3.键盘输入语句

介绍:要实现计算机接收用户的输入信息,则需要使用键盘输入语句

语法步骤:

在键盘输入语句中需要一个扫描器(Scanner)及其包含的功能代码。由于一般情况下,编程的代码中并没有一开始就加载上扫描器。这就需要我们人为加载。加载的原则是从包开始,再到类,最后到其它(如方法等)。而Scanner是一个类,它包含在一个包里,故我们要按照这个顺序来一步步让计算机找到这个类,从而实现加载(路径的找法见上文java API文档)。只有我们加载好类后,才可以调用该类里包含的方法,从而实现我们想要的功能

综上,步骤如下:

第一步:导入包含Scanner的包

import java.util.Scanner;

第二步:创建该类的对象(即声明变量)

  Scanner 变量 = new Scanner(System.in);

其中new就表示创建的意思

第三步:调用Scanner里的功能

  String name = myscanner.next();

接收输入的字符串

  int name = myscanner.nextInt();

接收输入的int

………


4.四种进制

(1)类型与表示方式

例如:

二进制……0b1010

八进制……01234567

十进制……123456789(输出时的默认进制)

十六进制……0x123456789ABCDEF

(2)进制的转换

i.二、八、十六进制与十进制的相互转换联系高中算法一章

ii.二进制转八进制:从右开始,每三个一组,转成十进制即可(在二进制中,每三个表示的数的范围为0~7,故可以实现。在分组时,不够三位的可以补充0在前即可)。同理转十六进制,每四个一组

iii.八进制转二进制:从左开始,把每个数转换为三位二进制数(不足位的在前补充0)。十六进制的,则是每个数转换位四位的二进制数



(六) 位移运算符

1.引子:位移运算中的“位”其实是计算机最底层的存储数值的bit。bit里存储1与0,是二进制的算法。而这些1与0的共同组合出的整体叫“码”,每个1与0占据的不同地方就是不同的“位”。为了计算机能直接利用这些码,并用二进制的方式运算。人们将这些码分为了原码、反码与补码,方便识别负数,从而方便计算加减乘除(在人算二进制中,直接转换往往只能得到正数,故为了表达负数就出现了符号位。但是仍然用的1与0,对计算机来讲,非常难以辨别。于是人们又创造出原码、反码与补码,从而成功帮助计算机识别出符号位)。在进行运算时,一个数转换成带符号位的二进制(即原码),之后再转换成反码,最后转换为补码。计算机只有通过补码才能实现正确的运算。而我们人看运算结果时,是看的原码。

详细内容见知乎:

https://zhuanlan.zhihu.com/p/371184302

其中几条重点知识:


2.位运算符类型与运算规则:


说明:

(1)注意区分逻辑运算符,位运算符是针对一个数的二进制补码,而逻辑运算符针对是条件语句

(2)在运算时,计算机是看的补码,结果输出是原码

(3)运算方法:

例如已知两个补码:10010001 与 11110010

首先将补码竖着排列,依次对齐。在通过位运算符规则,一个一个位比较得结果

10010001

11110010

------------- (按位与)

10010000

注意:计算机在存储补码时,要按照字符类型进行存储且第一个位为符号位,故一般不会出现位数不相等的情况

下面是编程时的推导:

说明:这里2与3是int类型,4个字节,32个位(bit)

(4)

算术右移>>运算规则:

例如: int a = 1 >> 2

其中1表示要执行操作的数,2表示1转换后的补码整体向右移动两位,溢出部分删去,空出部分补符号位

| 00000001 |

| 0 00000 | 01

| 00000000 |

本质为原来的数除多少个2

算术左移<<运算规则:

例如:int b = 1 << 2

| 00000001 |

00 | 000001 |

| 00000100 |

本质为原来的数乘多少个2

逻辑右移>>>运算规则:

例如:int c = 1 >>> 2

| 00000001 |

| 000000 | 01

| 00000000 |



程序流程控制结构篇

一 什么叫程序流程

程序中执行代码的顺序。它包括三种基本流程:顺序、分支、循环


二、顺序控制

程序从上至下逐步执行的一种流程,中间没有任何判断和跳转

程序框图如下:

注意:在调用变量时,只能用之前所定义的,即前向引用


三 分支控制

(一) if-else

1.单分支型

基本语法:

if(条件表达式){

代码块;

}

说明:当且仅当条件表达为ture时才会执行代码块


2.双分支型

基本语法:

if(条件表达式){

代码块1;

}

else {

代码块2;

}

说明:当条件表达式成立执行代码块1,否则执行代码块2


3.多分支型

基本语法:

if(条件表达式1){

代码块1;

}

else if(条件表达式2) {

代码块2;

}

else if(条件表达式3) {

代码块3;

}

…………

else {

代码块N;

}

流程图:

说明:可以省略最后的else部分。当省略它时,若所有条件都不满足,则没有任何代码块执行。反之,当不省略时,若所有条件都不满足,则只会执行else所包含的代码块


4.嵌套分支型

顾名思义,在分支流程中再分支,如同树枝一样(为了可读性强,建议不要超过3层嵌套分支)


基本语法(举例一种):

if(条件1){

if(条件1.1){

if(条件1.1.1){

代码块;

}else

代码块;

}else

代码块;

}


(二)switch

基本语法:

switch(表达式){

case 常量1:

代码块1;

break;

case 常量:

代码块2;

break;

………

case 常量N:

代码块N;

break;

default:

代码块;

break;

}

说明:表达式对应一个值(其实只要有值返回,表达式为变量都可以),只可以为int,byte,short,char,enum(枚举),String。当表达式的值符合下方哪个常量(是从上往下依次检索),就执行哪个常量所对应的代码块,一直运行到break后跳出整个switch分支。若一个都不匹配,则执行default处的代码块


注意:

1.匹配的常量数据类型应当与表达式数值一致,或者可以自动转成可以相互比较的类型(例如char可以转换为int)

2.default可以省略

3.break未写,将不会跳出switch,而是顺序执行下一个代码块,一直运行到结尾或下一个的break(即穿透情况)


四 循环控制

(一) for

基本语法:;

for(循环变量初始化;循环条件;循环变量迭代){

循环执行的代码块;

}

例如:

for( int i = 1 ; i <= 10 ; i++){

System.out.println("你好,韩顺平教育");

}

说明:

(1)执行流程联系高中算法中的当型循环,流程图如下:

值得注意的是,迭代在循环执行代码块后进行

(2)括号内的初始化与变量迭代可以写在括号外的其它地方,但循环条件不可以,且循环条件两头的分号不可以省

(3)处于括号内的新定义的变量不能在for循环外的代码中使用

(4) for(;;)是死循环。利用cral + c实现终止程序退出

(5)可以初始化,迭代多个变量,变量间用逗号隔开


(二)while

基本语法:

while(循环条件){

循环代码块;

循环变量迭代;

}

说明:与for基本一致,只是基本要素位置不同而已。流程图如下:

值得注意的是,未写循环变量迭代,将会进行死循环



(三) dowhile

基本语句:

do{

循环代码块;

循环变量迭代;

}while(循环条件);

说明:与for、while一样,有循环语句的四要素(这里省略了变量初始化),只是位置不一样。但与这两个不一样的是,该语句无论如何都要先执行一遍,再进行循环。流程图如下:

与while一样,未写循环变量迭代,将会进行死循环


(四) 多重循环

介绍:在一个循环体中嵌套另一个循环体(一般嵌套使用两层,最多不要超过三层)

执行流程概要:可以采取换元法,把内层循环当作整体作为外层循环的代码块,从而简化思路。比如说,若外层的循环次数为m次,内层 的循环数为n次,则外层每进行一次,则内循环要完整进行n次,故总体内循环执行m*n次



五 跳转控制

(一) break

用于终止最近某个语句块的执行,一般用在switch或循环语句中

基本语法:

……

break;

……

为了能控制break语句的发生,往往搭配If语句使用。例如:


补充:

break语句可以配合标签(在break后面加上标签名称)来针对性地终止某一个代码块。标签的使用方法:在一个{}整体前面加上"【标签名称】: "即可。但由于使用标签会使代码的可读性变差,故实际开发中尽量不要使用标签。例如:

说明:当执行到break时,由于标签的存在,使得lable1标签所指的代码块终止,即外循环终止,从而直接跳出到最外层


(二) continue

用于结束本次循环,进行下一个循环

基本语法结果与break一样,也可以使用if来控制与使用标签来针对


(三) return

用于跳出方法,如果使用在主方法main中,将会直接退出程序

与上面的一样,基本语法不变

有关方法,将在之后讲解



数组篇

一 什么叫数组

顾名思义,数值的组合,可以理解为高中里的集合。通过使用数组,可以实现多个数值,多个变量的批量操作或者针对操作,从而简化代码。数组是一种数据类型,属于引用类型,故也会涉及基本数据类型等相关知识

二 数组的基本使用方法

(一)定义数组

基本语法:

数据类型 数组名称[] = new 数据类型 [大小];

例如:

int a[] = new int[5];

创建一个名为a的可包含5个int数值的数组

或者可以把[]放在第一个数据类型的后面

补充:可以只写 数据类型 数组名称[] 来声明,之后再创建new语句。注意此时内存并没有分配空间给数组,若没有new语句就直接赋值会报错


(二)针对性调用

当定义完数组并存储了一定数量的数值时,可以类似于变量一样,通过 数组名称[n] 表示调用某一个数组里的单独某个数值,其中[n]表示下标。注意n表示第n+1个数值,也就是说,第一个数值其实是第零个[0]


(三)赋值数值

基本语法

1.数组名称[n] = .......其中[n]表示下标

2.数据类型 数组名称[] = {a , b , c, ... };该方法又称为静态初始化

3.数据类型 数组名称[] = new 数据类型[]{……};该方法[]不可以填任何数字


(四) 调用数组元素个数

基本语法:类似变量,利用 数组名称.length 来表示


三 数组的使用细节

(一)数值与数组的数据类型要一致或能够进行自动转换或能够把小转大才行

(二)数组创建后,如果没有赋值,则计算机会以默认值赋值给所有元素。分别如下:

int……0

short……0

byte……0

long……0

float……0.0

double……0.0

char……\u0000 [十六进制]

boolean……false

String……null

(三)数组的下标从0开始且只能在范围内使用

(四)由于数组的数据类型为引用类型,故其数据实则为 对象。但数组[n]是基本数据类型,要涉及基本数据类型中的使用细节


四 数组的赋值机制

数组在默认情况下是引用传递,赋值的值本质是地址。不同于基本数据类型的赋值(值传递),在这里,一个值赋值给另一个会影响到本身。例如:

int[] arr1 = {1,2,3};

int[] arr2 = arr1;

arr2[0] = 10;

执行完后,不光是arr2第一个元素改变了,arr1也发生了变化

这里我们将详细讲解引用传递与值传递在计算机内存上的具体体现:

java在计算机上的内存也可以称为jvm的内存。在这里,内存大致可以分出三个区域:栈、堆、方法区。其中变量、数值(基本数值类型的)、地址在栈中存储。堆中存储地址所连接的详细数据。(这里的地址可以理解为路牌,它只起到指引作用,不能起到存储内容的作用。而它指引的目的地,才是引用数据类型的内容的集中处)


值传递:基本数据类型的一种赋值方式。它是在栈中进行的。例如:

int a = 10;

int b = a;

此时a赋值给b的操作实际为:a变量在栈中分得空间,由变量a指向该空间,该空间中存储int数值10。之后a将该空间数值复制给b变量指向的空间中。注意,复制的是数值本身。故此时改变b中数值,只在b指向的空间中执行,并不会影响a变量指向的空间。


引用传递:引用数据类型的一种赋值方式,变量在栈中分得一定空间来存储地址并在堆中一定空间中存储实在的数值内容。而地址作为索引,使计算机与堆中该空间联系。例如之前的例子:

int[] arr1 = {1,2,3};

int[] arr2 = arr1;

arr2[0] = 10;

数组arr1在栈中与堆中分别获得一定空间,在前者存储地址,后者存储数组中的数值(存储的数值在该区域中会被分到更小的区域,互不干扰,从而实现了下标功能)。之后地址与堆相联系。在arr1赋值给arr2时,arr1在栈中复制地址给arr2(注意,赋值的是地址!),使得arr2所指向的地址又与堆中相同空间联系(路牌内容一样,目的地只有一个,故两者都会来到同一个地方)。若改变arr2中的数值,其实是计算机通过arr2中的地址找到堆中相应位置后,再改变数值。故改变后,arr1也跟着改变。

注意:若出现这样的赋值:

int[] arr1 = {1,2,3};

int[] arr2 = {1,2,3,4};

arr1 = arr2;

此时,由于arr2直接赋值给arr1,使得arr1原先地址替换,导致原来的数组arr1由于没有地址联系而被计算机清除


五 数组的拷贝

由于数组的赋值的不同,需要靠其它方式进行像值传递一样的复制方式

基本方法:在堆中开辟出新的数组区域,将原来的数组所含数值复制到该新区域,并让新的数组建立出联系该区域的地址

基本语法:

int[] arr1 = {……};

int[] arr2 = new int[arr1.length];

//开辟出新的数组区域

for(int i = 0;i < arr1.length;i++){

arr2[ i ] = arr1[ i ];

}

//将数组arr1中的数依次复制到arr2中


六 数组的反转

将数组中的数值根据下标倒置过来

效果例如:

{10,20,30,40} >>>>{40,30,20,10}

基本思路1:

基本代码1:

说明:temp变量是用于交换数值的中间变量,就如同倒水一样,把两个杯子里的水互换时,必须要第三个杯子帮助。而temp就是这第三个杯子。


基本思路2:通过创建新的数组来存储倒序后的数值,再把这个数组复制到目标数组

基本代码2:

说明:由于要逆序复制,数组1复制到数组2时要倒着进行,这也是 i-- 的原因。但到数组2时要正着导入,这便是 j++ 的原因


七 数组的扩容与缩减

能够实现动态地增加或减少数组中的元素个数的方法

基本思路与代码:

说明:缩减的方法,就是在扩容的思路上,大致上把加改减即可


八 基本排序

用于将多个数据按照指定的顺序进行排列的方法

(一)分类

1.内部排序:所需要排序的数据可以全部加载到内存处理器中来进行排序(包括:交换式排序法、选择式排序法和插入式排序法)

2.外部排序:所需要排序的数据不能完全加载到内存处理器中,需要在外部存储来进行排序(包括:合并排序法和直接合并排序法)


(二) 冒泡排序法

基本思路:对待排序的数按照序号从后往前依次比较相邻数的大小,改变相邻数的顺序使得较大的数从前移向后部,实现将数从小到大排列

说明:每次比较时,都是从前往后依次两个两个比较。第一次比较24与69,第二次比较69与80,依次类推。然后逐渐将大的数通过两两交换,排到后面去。


过程特点:

说明:

1.第2点与第3点说明是一个双层循环结构

2.第4点涉及的代码为常见的交换数值代码

3. 外循环次数与内循环次数有相同的值(即4),说明可以套用相同的变量,且4又恰好等于数组元素个数减1,可以方便实现“先死后活”

4.每次比较时,内循环次数再逐渐变少,涉及 减法的计算


参考代码:



九 顺序查找

一种按照从前往后的顺序在数组中找到目标数值的方法

基本语法:


说明:利用index变量纪录是否找到所需要的值,若找到则index变量原来的值会改变,否则将保持原来的值。这时,只用判断index是否变化就可以判断是否找到


十 二维数组

如果将之前学的那一列数组当作一维数组,则二维数组则是将多个一维数组组合起来。

例如:

数组1: 1,0,5,8

数组2: 4,5,8,6

数组3: 1,6,9,0

那么二维数组为:

1,0,5,8

4,5,8,6

1,6,9,0


(一) 二维数组的内存存放方式

类似于一维数组的地址操作,在这里,不同在于在堆中又存放了一个地址来连接一维数组


(二)创建二维数组

基本语法1:

数据类型[] [] 数组名称 = new 数据类型[大小1] [大小2]

(类比一维数组的创建方式)

说明:

大小1表示二维数组中包含了多少个一维数组,大小2表示一个一维数组包含多少元素。在赋值时,[][]也表示相同的指代。例如:arr[1][2] = 1;表示把下标为1的一维数组中的下标为2的元素赋值为1

同一维数组,也可以先声明,再new。而且二维数组也有相同的默认赋值


补充:

二维数组可以出现“列数不确定”现象。即二维数组中的一维数组中的元素不一定要相同。例如:

1 ,

2,1

1,0,0

那么此时创建方式略有不同:

数据类型[] [] 数组名称 = new 数据类型[大小1] []

(注意:没有填 大小2 ,就导致了一维数组其实并没有new一个实际的空间出来,此时里面全为空null)

之后要单独地为每个一维数组开(new)空间:

数组名称[下标] = new int[大小]

最后依次赋值


基本语法2:

数据类型 数组名称[][] = {{值1,值2...},{值...}}

说明:

[][]位置可以直接放在数据类型的后面,也可以像这样:int[] y[] = ……

该方法可以免去赋值的代码


(三)遍历二维数组的方法

基本语法

说明:

(注意关注循环部分)

对二维数组来说,arr.length得到的是有多少个一维数组。arr[i].length才是得到的某个一维数组中有多少个元素

arr[ i ][ j ]是遍历二维数组的关键,而嵌套循环的主要作用就是帮助改变i与j的值


杨辉三角作业参考:

评价:未考虑到只有1行或2行的情况,这里少了if去判断。未能简化思路:除了首末就是中间元素,刚好可以分别赋值,由此考虑if-else并使用逻辑条件

老师思路(更简洁):



面向对象编程篇(基础)

一 类与对象

(一) 什么是对象与类

一个程序就是一个世界,在这个世界中存在许多的事物(如树,猫,狗,人……)。而这些事物又存在许多特征 ,包括外貌的特征,心理的特征,行为的特征等等。我们把这些事物称为对象,一个对象主要具备属性,行为的特征(就像写个人信息表一样,属性就是指那些如身高、体重、年龄一样的数据,而行为就像是指你喜欢做什么,口头禅是什么一样的数据)。每个对象都是独一无二的(就像人一样),但存在一些对象具有一些某方面上的相似性,我们就把这些对象统一起来,分门别类,把他们整体称为类(就好比生物中的界门纲目科属种一样)


(二)类在编程中解决的问题

如上文说到,类中包含的对象具有一些方面的相似性,或者说这些对象都有同样的可描述的方面,比如说人这个类里,每个人都有性别,年龄,身高,体重等等可描述的方面。而类就是以这些个方面来归纳的。如果我们创建一个类,那么这些个类中就有这些个描述对象的方面,就像是一个对象生成器一样,一个特征编译器的模子,只要按照这个类,就能轻松创造出具有一定属性,行为的对象,方便管理对象的数据

类是一种自定义的数据类型,可以添加多种属性,行为来归纳数据,这些数据实际上就是对象。

由于类其优越的数据管理能力,可以帮助我们在创建,调用对象时,可以一下子动用整个对象的全部数据来实现某些功能且不会出现混乱情况(在传统的直接定义法定义某个对象时如int name = ....;int age = ....会使数据特别分散,尤其是要用到多个对象时,如果不好好命名变量名称,是极容易弄乱的。利用数组法虽然可以整理数据,但在调用数据时不是很直观,比如int[] dog = {1,5,45};由于调用其中单独数据时只能用dog[下标]表示,如果我不提前记忆{}内每个数据代表什么含义时,谁知道谁是谁?而且数组往往只能整合一种数据类型,比如我想添加狗的姓名时,由于是字符串类型,就无可奈何。而类则是解决了上面两者情况的问题,并且整合了两者的优点)


(三) 创建类与对象

1.创建类:

基本语法:

class 类名 {

数据类型 属性1;

数据类型 属性2;

数据类型 属性3;

.........

}

注意:

要在主类main的{}外定义新的类;

数据类型可以有数组

例如(一个描述猫的类):

2.创建一个对象

基本语法:

类名 对象名 = new 类名();

对象名.属性1 = ...;

对象名.属性2 = ....;

……

例如:

注意:对象的创建一般放在主类里


(四) 对象与类在内存的存在形式

由于类是引用数据类型,故基本原理与数组一样,这里不再赘余(结合之前的知识来理解图即可)


(超2w字了。。。可恶(#-.-))

(等以后笔记可以拓展了再更新)





【零基础 快速学Java】韩顺平 零基础30天学会Java的评论 (共 条)

分享到微博请遵守国家法律