2.java编程基础
1.标识符与命名规范
标识符是给Java中的类、方法、变量、包命名的符号:
只能由字母、数字、下划线、美元符号组成,并且不能以数字开头。
Java标识符大小写敏感,长度无限制
标识符不可以是Java关键字和保留字
2.变量的定义和赋值
变量赋值语法如下:
int a, b, c; // 声明三个int型整数:a、 b、c
int d = 3, e = 4, f = 5; // 声明三个整数并赋予初值
byte z = 22; // 声明并初始化 z
String s = "runoob"; // 声明并初始化字符串 s
double pi = 3.14159; // 声明了双精度浮点型变量 pi
char x = 'x'; // 声明变量 x 的值是字符 'x'。
3.常量
常量与变量的语法类似,只在变量声明语法前加上final关键字即可。
变量是可以改变值的量,而常量一旦被赋值后,就不可以改变了。
常量名的命名,一般要求所有字母大写,单词之间使用“_”隔开。
常量声明语法如下:
//声明一个常量
final 数据类型 常量名 = 常量值;
4.数据类型转换
主要分为两种:自动类型转换(隐式转换)和强制类型转换(显式转换)。
首先是自动类型转换
整型、实型(常量)、字符型数据可以混合运算。
运算中,不同类型的数据先转化为同一类型,然后进行运算。
转换从低级到高级:
byte,short,char—> int —> long—> float —> double
int num1 = 10;
double num2 =num1;
int类型的常量可以直接赋值给char、short、byte,只要不超过它们能够表示的值的范围即可。
强制类型转换
强制性地将占用字节数多的数据类型的数据转换成占用字节数少的数据类型的数据,
但这个转换过程可能会存在数据精度丢失的问题
数据类型 变量名 = (数据类型)变量值;
Scanner的使用
首先需要使用 new 关键字创建Scanner的对象,再通过Scanner类的next()方法获取用户在控制台输入的字符串,
通过nextByte()、nextShort()、nextInt()、nextLong()、nextFloat()、nextDouble()获取用户在控制台输入的基本数据类型
Scanner s = new Scanner(System.in);
next() 与 nextLine() 区别
next():
1、一定要读取到有效字符后才可以结束输入。
2、对输入有效字符之前遇到的空白,next() 方法会自动将其去掉。
3、只有输入有效字符后才将其后面输入的空白作为分隔符或者结束符。
next() 不能得到带有空格的字符串。
nextLine():
1、以Enter为结束符,也就是说 nextLine()方法返回的是输入回车之前的所有字符。
2、可以获得空白。
2.2 运算符与表达式
算数运算符:
+,-,* ,/(整数之间结果仍是整数)。
% 取余 - 左操作数除以右操作数的余数
++ 自增: 操作数的值增加1
-- 自减: 操作数的值减少1
前缀自增自减法(++a,--a): 先进行自增或者自减运算,再进行表达式运算。
后缀自增自减法(a++,a--): 先进行表达式运算,再进行自增或者自减运算
赋值运算符:
=,+=,-=,*=,/=,%=
关系运算符也称作比较运算符,关系运算符的运算结果为布尔类型
<,>,<=,>=,==,!=
如果对那就是true,不对就是flase。
逻辑运算符
&& 与运算符:当两个条件都为真时,返回真,否则返回假。
| 或运算符:当两个条件中至少有一个为真时,返回真,否则返回假。
! 非运算符:用于反转条件的逻辑值,如果条件为真,则返回假;如果条件为假,则返回真。
^ 异或运算符:当两个条件不相同时,返回真,如果相同则返回假。
& 按位与运算符:对两个数的每一位进行与操作,都为1时结果为1,否则为0。
| 按位或运算符:对两个数的每一位进行或操作,任意一位为1结果就为1,都为0时结果为0。
~ 按位非运算符:对一个数的每一位取反,即0变为1,1变为0。
位运算
是直接对二进制进行的计算,性能极高,很多框架中都会使用位运算。位运算在实际开发中应用较少,因为相较于这些细微的性能提升,代码可读性更加重要,因此了解即可
三元运算符
条件表达式 ? 表达式1 : 表达式2;
//计算较大值时,如果num1比num2大,则num为较大值
int max = num1>num2? numn1:num2;
2.3 选择结构
if语句的语法格式如下所示:
程序执行到if语句后会进行判断:当条件表达式1为true时,执行代码块1;否则,当条件表达式2为true时,执行代码块2;否则,当条件表达式3为true时,执行代码块3;否则,执行代码块n。其中,一个if语句之后可以有0至多个else if语句,可以有0或1个else语句。
1.如果if选择结构只需执行一条语句,那么可以省略{}。为了提高代码的易读性,建议不要省略{}。
2. {}中的代码语句也称为代码块,在代码块定义的常量或变量的作用域仅限于代码块中,在代码块之外不能被使用。
switch语句一般用于做一些精确值的判断,其语法格式如下所示。
switch语句会根据表达式的值从相匹配的case标签处开始执行,一直执行到break语句处或者是switch语句的末尾。如果case全都不匹配,则进入default语句。
switch语句判断的变量中,类型只能是byte、short、int、char、String和枚举,
因此它的适用范围较窄,但对于精确值的判断,switch依然是非常方便的。
区别:
if语句和switch语句都可以实现逻辑判断,但它们的使用场景有所不同。if语句一般用于区间值的判断,而switch语句只能用于确定值的判断。凡是switch语句能够实现的,if语句都可以实现,反之则不行。
2.4 循环结构
for循环执行的次数是在执行前就确定的,语法格式如下
for(循环初始化表达式;循环条件表达式;循环后操作表达式){
//循环体
}
for(int x = 10; x < 60; x = x+1) {System.out.print("value of x : " + x );System.out.print("\n");}
while是最基本的循环,它的结构为
while (条件表达式) {//循环体
}
只要布尔表达式为 true,循环就会一直执行下去。
do…while 循环
对于 while 语句而言,如果不满足条件,则不能进入循环。但有时候我们需要即使不满足条件,也至少执行一次。
do…while 循环和 while 循环相似,不同的是,do…while 循环至少会执行一次。
do{
//循环体
}while(条件表达式);
do{System.out.print("value of x : " + x );x++;System.out.print("\n");}while( x < 10 );
break用于强行退出循环,不执行循环中剩余的语句。
continue则只能终止某次循环,继续下一次循环。
2.5 方法
将功能拆分成一个一个方法,需要完成该功能时只需要调用对应方法
想要使用方法时,必须先声明该方法,才能在其它代码中调用。方法声明语法格式如下所示。
修饰符 返回值类型 方法名(参数类型 参数名1 ,参数类型 参数名2,……){
// 方法体;
return;
}
/** 返回两个整型变量数据的较大值 */
public static int max(int num1, int num2) {int result;if (num1 > num2)result = num1;elseresult = num2;return result;
}
(1)修饰符:用于控制方法的访问权限,目前学习阶段全部写为public static即可。
(2)返回值类型:方法需要返回给调用者数据的数据类型,如无返回值,必须声明返回值类型为void。
(3)方法名:方法的名字,命名规范在标识符规范的基础之上,采用首字母小写的驼峰命名规则。
(4)形参列表:由参数类型和参数名组成,也称作形式参数(形参),形参可以为任意多个,用于调用者给方法内部传递数据。
(5)方法体:该方法需要实现的具体逻辑。
(6)返回值:方法执行完毕后提供给调用者的数据。如果定义了返回值类型,那么返回值和返回值类型必须保持一致;如果定义的返回值类型为void,那么需要省略返回值,也就是直接用语句“return;”返回或者省略该语句直至该方法执行结束。当方法在执行过程中遇到return语句,就会返回而结束该方法的执行。
Java 支持两种调用方法的方式,根据方法是否返回值来选择。
当程序调用一个方法时,程序的控制权交给了被调用的方法。当被调用方法的返回语句执行或者到达方法体闭括号时候交还控制权给程序。
当方法返回一个值的时候,方法调用通常被当做一个值。例如:
int larger = max(30, 40);
如果方法返回值是void,方法调用一定是一条语句。例如,方法println返回void。
方法重载
在同一个类中,允许存在一个以上的同名方法,只要它们的参数个数或者参数类型不同即可,这种现象称作方法重载。需要注意的是,方法重载只与参数和方法名有关,返回值类型不同,不构成方法的重载;形参的名称不同,不构成方法的重载;方法修饰符不同,不构成方法的重载。
方法重载可以让程序更清晰易读。执行密切相关任务的方法应该使用相同的名字。
重载的方法必须拥有不同的参数列表。
方法递归
方法直接或间接调用方法本身,则称该方法为递归方法。合理的使用递归,能够解决很多使用循环难以解决的问题。
2.6数组
数组就是一种能够存放相同数据类型的有序集合,或者说它是一个存储数据的容器。可以创建出一个指定长度的数组,这样就可以存储对应条数的数据了。
在Java中,数组的创建方式分为3种,语法格式如下所示。
1.通过索引操作元素
数组元素的操作都是通过索引(也称作下标)进行的,当创建了一个长度为n的数组后,它的索引范围是[0, n-1]。
2.数组的遍历
当数组元素很多时,不可能一个一个使用索引获取元素,而是希望能够通过循环的方式取出数组中每一个元素,这个操作称作遍历。数组的遍历一般使用for循环遍历,从0遍历到数组长度-1即可。
如果只是想获取数组中的每一个元素,并不需要给数组元素赋值,也不需要操作索引,还有一种更为简便的遍历方式:foreach循环,又称作增强for循环。
foreach循环的语法格式如下所示
3.获取数组的最值
当需要获取到数组的最大值或最小值时,通过常规的思路可能不太好处理,此时可以使用“假设法”。首先假设索引0处的元素是最大值,之后遍历整个数组,每次遍历取出当前元素与所假设的最大值进行比较,如果当前元素比假设的最大值还大,就再假设该元素是最大值,直到数组遍历完毕为止,最后所假设的最大值就是真正的最大值。
4.通过值获取索引
有时可能需要查询数组中某个值所在的索引位置,这个操作也可以通过遍历实现,但需要注意,待查找的值可能在数组中不存在,因此需要先假设待查找值的索引为-1。因为-1这个值不可能是数组的索引,因此当遍历结束后如果索引还是-1,就说明没有找到该值。
5.数组元素的反转
有时候可能需要反转一个数组,将数组元素首尾互换,这可以借助一个新的数组。
数组排序算法
1.冒泡排序
核心思想:在要排序的序列中,对当前还未排好序的全部元素,自上而下对相邻的两个数依次进行比较和调整,让较大的数往下沉,较小的数往上冒,就好像水泡上浮一样,如果它们的顺序错误,就把它们交换过来,
import java.util.Arrays;public class ArrayDemo {public static void main(String[] args) {// 算法一:冒泡排序int[] arr = {3, 9, 8, 2, 5, 4, 6, 7, 1, 0};System.out.println(";Before "; + Arrays.toString(arr));sort(arr);System.out.println(";After "; + Arrays.toString(arr));// 算法二:选择排序}// 把 arr 进行从小到大排序public static void sort(int[] arr) {// 步骤一:理解算法的核心思想(概念、图解、动画)// 步骤二:进行编程分析// 【内】发现一个循环:从左到右遍历数组,arr[i] 和 arr[i+1] 比较,顺序不动,逆序则交换// 1)什么循环:遍历的区间是[0, length-2],知道边界,用 for 更合适// 2)循环条件(结束条件):走到了 length-2 这个位置,不再往下// 3)循环体:比较arr[i]和arr[i+1],顺序不动,逆序交换// 【外】发现一个循环:每次都遍历一次数组,这一次比上一次数组的规模变小,我也不知道具体在遍历什么// 1)什么循环:遍历的区间就是数组的长度,length-1,当被砍到剩下1个元素,就结束// 知道边界,用 for 更合适// 2)循环条件(结束条件):当前处理的数组的长度剩下1的时候,可以不用继续了// 3)循环体:一个什么操作,每次给一个数组,这个操作都能把最大值放在当前数组的最右边// 当哪一个循环的循环体里说到“什么操作”,那当前这个循环就是外循环// 步骤三:编码for (int i = arr.length - 1; i > 0; i--) { // i 表示当前数组的最后一个有效位置moveFastToLast(arr, i);}}// 已知数组 arr 和最后一个有效位置,把最大值挪到这个endPositionprivate static void moveFastToLast(int[] arr, int endPosition) {for (int i = 0; i <= endPosition - 1; i++) {if (arr[i] > arr[i + 1]) {int tmp = arr[i];arr[i] = arr[i + 1];arr[i + 1] = tmp;}}}
}
2.选择排序
核心思想:在要排序的一组数中选出最小(或者最大)的一个数与第1个位置的数交换;然后在剩下的数中再找最小(或者最大)的与第2个位置的数交换,依次类推,直到第n-1个元素(倒数第二个数)和第n个元素(最后一个数)比较为止,每一轮排序都是找出它的最小值或者最大值的过程,
import java.util.Arrays;public class ArrayDemo2 {public static void main(String[] args) {int[] arr = {3, 9, 8, 2, 5, 4, 6, 7, 1, 0};System.out.println(";Before "; + Arrays.toString(arr));sort(arr);System.out.println(";After "; + Arrays.toString(arr));}public static void sort(int[] arr) {// 步骤一:理解算法的核心思想(概念、图解、动画)// 步骤二:进行编程分析// 【内】循环1:从左到右,找到最小值,和首位互换// 什么循环:[首位,末尾],知道边界,用for更合适// 循环条件:走完每一个元素// 循环体:比较,找到最小值,和首位互换// 【外】循环2:遍历数组,进行神秘操作,每次遍历的数组比上一轮的数组长度减一,从前面减// 什么循环:边界确定,用for// 循环条件:当前要遍历的数组的长度为1的时候,结束// 循环体:输入当前数组,和首位位置,进行神秘操作// 步骤三:写代码for (int i = 0; i < arr.length; i++) { // i 表示当前数组的首位moveMinToFirst(arr, i);}}// 遍历 arr,把最小值和首位互换private static void moveMinToFirst(int[] arr, int starIndex) {int minIndex = starIndex;for (int i = starIndex; i <= arr.length - 1; i++) {if (arr[minIndex] > arr[i]) {minIndex = i;}}int tmp = arr[starIndex];arr[starIndex] = arr[minIndex];arr[minIndex] = tmp;}
}
二分查找法
又称折半查找法,其算法思想是每次查找数组最中间的值,通过比较大小关系,决定再从左边还是右边查询,直到查找到为止。二分查找法的优点是比较次数少,查找速度快,平均性能好;其缺点是要求待查表为有序表,且插入、删除操作困难。因此,折半查找法适用于不经常变动而查找频繁的有序列表,二分查找法依然需要使用到循环,但由于不知道循环次数,所以最好使用while循环实现。
public class BinearySearchDemo {public static void main(String[] args) {int[] arr = {9, 45, 2, 8, 1, 0, 13};System.out.println(hasValue(arr, 8));System.out.println(hasValue(arr, 110));}// 二分查找public static boolean hasValue(int[] arr, int target) {
// 步骤一:了解算法的意图//比较中间位置和// 步骤二:// 发现是循环// 什么循环?(for还是while):不知循环次数while// 循环条件?(结束条件):找到了,长度0// 循环体:用左边界left和右边界right控制// 计算出mid = (left+right)ǘ// 比较arr[mid] 和 target// 如果相等,返回true,如果target比较小,则left=mid + 1// 如果target比较大,则right=mid - 1int left = 0;int right = arr.length-1;int mid = 0;while (left<=right){ //>为-1mid = (left + right)ǘ;if (target>arr[mid]){left = mid + 1;}else if (target<arr[mid]){right = mid - 1;}else {//即相等return true;}}return false;}
}
方法中的可变参数
一个方法中的参数个数不确定,但参数的类型确定时,可以使用可变参数。在实际处理时,可变参数会被当作数组进行处理。
public static viod method(数据类型 ...参数名)
二维数组
//数据类型[][] 数组名 = new 数据类型[m][n];
int[][] a = new int[2][3];
Arrays工具类
Arrays是Java中提供的操作数组的工具类,通过Arrays类,可以很方便地操作数组。Arrays中提供了大量的方法,其中常见方法如下表所示。