JAVA基础—Level1
软件:使用IDEA 或 ECLIPSE
JDK:java development kit (java开发者工具包)------配置环境变量
JRE:java runtime environment (java运行环境)
运行第一个程序,打印HelloWorld
文件名:Hello.java
public class Hello{
public static void main(String []args){
System.out.println("Hello World");
}
}
运行方式:
1、软件运行
2、cmd 命令窗口
javac Hello.java -----生成 Hello.class 文件
java Hello -----运行程序
运行结果:Hello World
1、注释
1、行内注释://
2、多行注释:/* */
3、文档注释:/** */ (Javadoc生成文档注释)
@author 标识一个类的作者 @author description
@deprecated 指名一个过期的类或成员 @deprecated description
@exception 标志一个类抛出的异常 @exception exception-name explanation
@param 说明一个方法的参数 @param parameter-name explanation
@return 说明返回值类型 @return explanation
@see 指定一个到另一个主题的链接 @see anchor
@serial 说明一个序列化属性 @serial description
@since 标记当引入一个特定的变化时 @since release
@throws 标志一个类抛出的异常 @exception exception-name explanation
@version 指定类的版本 @version info
(在这里的只是部分具体可以去网站搜索)
利用 cmd 命令窗口 生成 Hello.java 的文档
javadoc -encoding UTF-8 -charset UTF-8 Hello.java
2、标识符、命名规范
标识符命名的规则 :
1、只能由字母(a-z,A-Z),数字(0-9),下划线(_)和美元符号($)组成
2、不能以数字开头
3、不能与关键字重名
4、严格区分大小写
命名规范:
类命名规范:首字母大写,后面每个单词首字母大写(大驼峰式)。 HelloWorld
方法命名规范:首字母小写,后面每个单词首字母大写(小驼峰式)。 deleteNum
变量命名规范:首字母小写,后面每个单词首字母大写(小驼峰式)。 setTime
常量命名规范:全部都大写,有多个用下划线(_)。 MAX_A
3、基本数据类型和包装类
基本类型:byte 对应的包装类Byte 二进制位数:8
基本类型:short 对应的包装类Short 二进制位数:16
基本类型:int 对应的包装类Integer 二进制位数:32
基本类型:long 对应的包装类Long 二进制位数:64
基本类型:float 对应的包装类Float 二进制位数:32
基本类型:double 对应的包装类Double 二进制位数:64
基本类型:char 对应的包装类Character 二进制位数:16
基本类型:boolean 对应的包装类Boolean 二进制位数:8
Integer a = new Integer(3); // 定义Integer包装类对象
int b = 2; // 定义基本类型值
装箱:把基本类型转换成包装类,使其具有对象的性质,又可分为手动装箱和自动装箱
Integer x = new Integer(b); // 手动装箱
Integer y = b; // 自动装箱
拆箱:和装箱相反,把包装类对象转换成基本类型的值,又可分为为动拆箱和自动拆箱
Integer a = new Integer(3); // 定义Integer包装类对象
int m = a.intValue(); // 手动拆箱为int类型
int n = a; // 自动拆箱为 int类型
另外(字符的拓展、乱码问题):
中文汉字在不同字符集编码下的字节数(一般用的是 utf-8)
ISO-8859-1 一个汉字占1个字节
GB2312 一个汉字占2个字节
GBK 一个汉字占2个字节
ASCII 一个汉字占1个字节
Unicode: 一个汉字占2个字节
UTF-8 一个汉字占3个字节(一般是3个字节)
4、转义字符
\n 换行 \r 回车 \f 换页符 \b 退格
\0 空字符 \s 空格 \t 制表符 \" 双引号
\' 单引号 \\ 反斜杠
5、引用数据类型
引用数据类型包括
1、类: Object object= new Integer(10);
2、接口:接口不能直接new进行实例化,可以引用实现接口的类。
3、数组:int[] a=new int[10];
引申的问题:Java中==和equal的区别
1、==为关系运算符、equals()是方法,结果都返回的是布尔值
2、Object的 == 与equals()比较的都是地址,作用相同
比较基本类型:只能用==,不能用equal,这里的==比较的是两个变量的值
比较包装类型:==比较内存地址,equal比较的是值,包装类是new出来的,不同的对象地址肯定不同
比较String类型:==比较的是内存地址,equal比较的是值
比较对象:==和equal比较的都是内存地址
String str1 = "Hello";
String str2 = new String("Hello");
String str3 = str2; // 引用传递,同一对象 (str2和str3地址相同)
System.out.println(str1 == str2); // false(地址不同)
System.out.println(str1 == str3); // false(地址不同)
System.out.println(str2 == str3); // true (地址相同)
String str4 = "Hello";
String str5 = new String("Hello");
System.out.println(str1 == str4); // true (基本类型比较值)
System.out.println(str2 == str5); // false(地址不同)
System.out.println(str1.equals(str2)&&str2.equals(str3)); // true(都是比较内容)
6、类型转换
1、自动类型转换:低转高(转换前的数据类型的位数要低于转换后的数据类型,如(float转double))
char转int: char c='a'; int i= c;
2、强制类型转换:高转低(转换的数据类型必须是兼容的)
int转byte: int i = 123; byte b = (byte)i;
7、变量与常量
变量声明并赋值:
type identifier [ = value] 如:int a = 1;
变量类型作用域:
类变量:独立于方法之外的变量,用 static 修饰。
类变量也称为静态变量,在类中以 static 关键字声明,但必须在方法外。
静态变量在第一次被访问时创建,在程序结束时销毁。
实例变量:独立于方法之外的变量,不用 static 修饰。
实例变量声明在一个类中,但在方法、构造方法和语句块之外。
实例变量在对象创建的时候创建,在对象被销毁的时候销毁;
局部变量:类的方法中的变量。
局部变量声明在方法、构造方法或者语句块中;
局部变量在方法、构造方法、或者语句块被执行的时候创建,执行完成后被销毁;
常量:final
final int THRESHOLD = 5;
static final double PI = 3.1415926;
final void make(){ }
final class A{ }
final关键字可以用来修饰类、方法和变量(包括成员变量和局部变量)。
当final修饰变量时,被修饰的变量必须被初始化(赋值),且赋值后不能修改其值;
当final修饰方法时,被修饰的方法无法被所在类的子类重写;
当final修饰类时,被修饰的类不能被继承,且final类中的所有成员方法都会被隐式地指定为final方法
8、运算符
算术运算符:
+ 加法 - 相加运算符两侧的值
- 减法 - 左操作数减去右操作数
* 乘法 - 相乘操作符两侧的值
/ 除法 - 左操作数除以右操作数
% 取余 - 左操作数除以右操作数的余数
++ 自增 - 操作数的值增加1
-- 自减 - 操作数的值减少1
赋值运算符:
= 简单赋值运算符,C=A+B将把A+B得到的值赋给C
+= 加和赋值操作符,C+=A等价于 C=C+A
-= 减和赋值操作符,C-=A等价于 C=C-A
*= 乘和赋值操作符,C*=A等价于 C=C*A
/= 除和赋值操作符,C/=A等价于 C=C/A
(%)= 取模和赋值操作符,C%=A等价于C=C%A
<<= 左移位赋值运算符,C<<=2等价于C=C<<2
>>= 右移位赋值运算符,C>>=2等价于C=C>>2
&= 按位与赋值运算符,C&=2等价于C=C&2
^= 按位异或赋值操作符,C^=2等价于C=C^2
|= 按位或赋值操作符,C|=2等价于C=C|2
关系运算符:
== 左右操作数相等则条件为真。
!= 左右操作数不相等则条件为真。
> 左操作数的值大于右操作数的值条件为真。
< 左操作数的值小于右操作数的值条件为真。
>= 左操作数的值大于或等于右操作数的值条件为真。
<= 左操作数的值小于或等于右操作数的值条件为真。
逻辑运算符:
&& 逻辑与运算符。两个操作数都为真,条件为真。
|| 逻辑或操作符。两个操作数一个为真,条件为真。
! 逻辑非运算符。用来反转操作数的逻辑状态。如果条件为true,则逻辑非运算符将得到false。
位运算符:
int A = 60; /* 60 = 0011 1100 */
int B = 13; /* 13 = 0000 1101 */
& 与 (A&B),得到12, 即0000 1100
| 或 (A|B), 得到61, 即0011 1101
^ 异或 (A^B), 得到49, 即0011 0001
~ 非 (~A), 得到-61,即1100 0011
<< 按位左移 A<<2, 得到240,即1111 0000
>> 按位右移 A>>2, 得到15, 即1111
>>> 逻辑右移补零 A>>>3,得到7, 即0000 0111
条件运算符:
?: int b =(a == 1) ? 20 : 30;----> a 等于 1 则 b=20,否则 b=30
instanceof 运算符:判断该对象是否是一个特定类型(类类型或接口类型)。
( Object reference variable ) instanceof (class/interface type)
String name = "James";
boolean result = name instanceof String; //由于name是String类型,返回true
9、包机制
1、域名倒写 src下新建包,命名为www.baidu.com,将域名倒置作为包名即:com.baidu.www
2、定义包 package (定义包先于导入包)
3、导入包 import
4、为了防止命名冲突
package com.baidu.www;
import java.io.IOException;
10、流程控制
Scanner 对象的基本语法:
Scanner s = new Scanner(System.in); // 用于用户输入
顺序结构:程序默认结构,从上而下执行代码
选择结构:
单选择 if(xxx){}
双选择 if(xxx){} else if(xxx){}
多选择 if(xxx){} else if(xxx){} else{}
多选择 switch(xxx){
case a : xxx; break;
//(如果满足a,case a 没有break,则会执行了a再执行下面的 case)
case b : xxx; break;
default : xxx;
//这里的default相当于多选择的 else{}
}
循环结构:while(xxx) //满足条件再执行,直到不满足条件或者break退出循环
do{}while(xxx) //先执行一遍,再判断条件,直到不满足条件或者break退出循环
for(int i=0;i<100;++i){} //直到不满足条件或者break退出循环(左边为循环100次)
增强for(xxx) /* for(声明语句 : 表达式){}
声明语句:声明新的局部变量,该变量的类型必须和数组元素的类型匹配。
表达式:表达式是要访问的数组名,或者是返回值为数组的方法。
例子:
int [] numbers = {10, 20, 30, 40, 50};
for(int x : numbers ){
System.out.print( x );
System.out.print(",");
}
打印 10,20,30,40,50, */
break: 跳出循环
continue:终止当前循环
return: 结束方法的运行
11、方法
什么是方法:
Java方法是语句的集合,它们在一起执行一个功能。
方法是解决一类问题的步骤的有序组合
可以解决代码重复编写的问题
方法包含于类或对象中,可通过方法名被引用
方法的定义:
修饰符 返回类型 方法名 (参数名) { 方法体代码; return 返回值; }
public static int getSum(int x, int y) {
int z= x + y
return z;
}
方法调用:
类名.方法,对象.方法
方法重写:( 除了{}、修饰符的可变,其他都一样 )
重写的作用范围是父类和子类之间,其参数必须相同,
在子类中将父类的成员方法的名称保留,重写方法体,
可修改(修饰符)访问权限(权限不能低于父类),
可修改返回类型的为父类返回类型或其类型的子类,
其只能抛出父类方法抛出异常的子类。
声明为 final、static、private 的方法不能被重写。
方法重载:
重载是发生在一个类里面,
被重载的方法,方法名相同,参数必须不同(参数类型/个数/顺序不同),
方法能够在同一个类中或者在一个子类中被重载。
命令行传参:(实际上就是把输入的信息放在 args 数组里面)
程序:
public class Demo {
public static void main(String[] args) {
for(int i=0;i<args.length;i++)
System.out.println(args[i]);
}
}
windows+r ,cmd 命令
javac Demo
java Demo aaa bbb ccc
程序会打印
aaa
bbb
ccc
12、数组
数组概念:
数组是存储同一种数据类型多个元素的集合,可以看成一个容器。
数组的定义:
1、数据类型 [] 数组名 = {数组内容,数组内容,......};
int [] a = {1,2,3,4,5};
2、数据类型 [] 数组名 = new 数据类型[数组大小];
int [] a = new int[5]; //动态初始化
int [] a = new int[]{1,2,3,3}; //静态初始化
注:数组中的类型相同,数组索引从 0 开始,所以索引值从 0 到 a.length-1。
数组的使用:
1、通过下标取到值
2、数组角标越界异常(ArrayIndexOutOfBoundsException)
3、for循环遍历
二维数组:
表示:int [][] a; int [] a[]; int a[][];
int [][] a = new int[2][3]; //动态初始化
int [][] a = new int[][]{{2,3,4}{5,7,9}}; //静态初始化
二维数组的最后一个元素为:a[a.length-1][a[a.length-1].length-1];
Arrays工具类
1、数组转换字符串 Arrays.toString(a);
2、数组元素进行升序排列 Arrays.sort(a);
3、元素都赋成特定值 Arrays.fill(a,10); //全部赋值为10
4、判断两个数组是否相等 Arrays.equals(a,b);
5、数组复制成特定长度的数组 Arrays.copyOf(a,10); //复制数组a的前10个数值到新的数组
6、查询目标数字的下标位置 Arrays.binarySearch(a, 5); //获取数字5的下标位置
7、字符串转换成list Arrays.asList(a);
13、二分查找
//二分查找数组前提:数组必须有序
public class Demo {
public static void main(String [] args){
int arr[]={10,20,30,40,50,60,70};
Scanner s=new Scanner(System.in);
int num =s.nextInt();
int index=getIndexByELE(arr,num);
System.out.println( "arr["+index+"]="+num);
}
private static int getIndexByELE(int arr[], int ele){
int minIndex=0;
int maxIndex=arr.length;
int midIndex=(minIndex+maxIndex)/2;
while(minIndex<=maxIndex){
if(arr[midIndex]==ele)
return midIndex;
if(arr[midIndex]<ele)
minIndex=midIndex+1;
if(arr[midIndex]>ele)
maxIndex=midIndex-1;
midIndex=(minIndex+maxIndex)/2;
}
return -1;
}
}
14、排序
import java.util.Arrays;
public class Demo1 {
public static void main(String[] args) {
int arr[] = { 24, 69, 80, 57, 13 };
popSort(arr);
selectSort(arr);
insertSort(arr);
shellSort(arr);
quickSort(arr, 0, arr.length - 1);
mergeSort(arr, 0, arr.length - 1);
radixSort(arr);
heapSort(arr);
System.out.println(Arrays.toString(arr));
// for (int i : arr) {
// System.out.print(i);
// System.out.print(",");
// }
}
// 冒泡排序
public static int[] popSort(int arr[]) {
for (int i = 0; i < arr.length - 1; i++) {
for (int j = 0; j < arr.length - 1 - i; j++) {
if (arr[j] > arr[j + 1]) {
int temp = arr[j];
arr[j] = arr[j + 1];
arr[j + 1] = temp;
}
}
}
return arr;
}
// 选择排序
public static int[] selectSort(int arr[]) {
for (int i = 0; i < arr.length - 1; i++) {
for (int j = 1 + i; j < arr.length; j++) {
if (arr[j] < arr[i]) {
int min = arr[j];
arr[j] = arr[i];
arr[i] = min;
}
}
}
return arr;
}
// 插入排序
public static int[] insertSort(int arr[]) {
for (int i = 1; i < arr.length; i++) {
for (int j = i; j > 0; j--) {
if (arr[j] < arr[j - 1]) {
int t = arr[j];
arr[j] = arr[j - 1];
arr[j - 1] = t;
}
}
}
return arr;
}
// 希尔排序(插入排序的优化)
public static int[] shellSort(int arr[]) {
for (int h = arr.length / 2; h > 0; h /= 2) { // 克努特序列 即把h/=2改成 h=(h-1)/3 效率会更高一点
for (int i = h; i < arr.length; i++) {
for (int j = i; j > h - 1; j -= h) {
if (arr[j] < arr[j - h]) {
int t = arr[j];
arr[j] = arr[j - h];
arr[j - h] = t;
}
}
}
}
return arr;
}
// 快速排序
public static int[] quickSort(int arr[], int left, int right) {
if (left < right) {
int i = left;
int j = right;
int key = arr[left];
while (i < j) {
while (i < j && arr[j] >= key)
j--;
arr[i] = arr[j];
while (i < j && arr[i] <= key)
i++;
arr[j] = arr[i];
}
arr[i] = key;
quickSort(arr, left, i - 1);
quickSort(arr, i + 1, right);
}
return arr;
}
// 归并排序
public static int[] mergeSort(int arr[], int low, int high) {
if (low < high) {
int mid = (low + high) / 2;
mergeSort(arr, low, mid); // 左拆开
mergeSort(arr, mid + 1, high); // 右拆开
merge(arr, low, mid, high); // 归并
}
return arr;
}
public static void merge(int arr[], int low, int mid, int high) {
int i, j, k;
int arr1[] = new int[high + 1];
for (k = low; k <= high; k++) {
arr1[k] = arr[k];
}
for (i = low, j = mid + 1, k = i; i <= mid && j <= high; k++) {
if (arr1[i] <= arr1[j])
arr[k] = arr1[i++];
else
arr[k] = arr1[j++];
}
while (i <= mid)
arr[k++] = arr1[i++];
while (j <= high)
arr[k++] = arr1[j++];
}
// 基数排序(不能用于负数排序)
public static int[] radixSort(int[] arr) {
int[][] bask = new int[10][arr.length];
int[] counts = new int[10];
int max = getMax(arr);
int len = String.valueOf(max).length();
for (int i = 0, n = 1; i < len; i++, n *= 10) {
for (int j = 0; j < arr.length; j++) {
int ys = ((arr[j] / n) % 10);
bask[ys][counts[ys]++] = arr[j];
}
int pos = 0;
for (int k = 0; k < counts.length; k++) {
if (counts[k] != 0) {
for (int h = 0; h < counts[k]; h++) {
arr[pos++] = bask[k][h];
}
counts[k]=0;
}
}
}
return arr;
}
public static int getMax(int[] arr) {
int max = arr[0];
for (int i = 1; i < arr.length; i++) {
if (max < arr[i])
max = arr[i];
}
return max;
}
// 堆排序
public static void heapSort(int[] arr) {
for (int i = (arr.length - 1) / 2; i >= 0; i--) {
adjustHeap(arr, i, arr.length);
}
for (int i = arr.length - 1; i > 0; i--) {
int temp = arr[i];
arr[i] = arr[0];
arr[0] = temp;
adjustHeap(arr, 0, i);
}
}
public static void adjustHeap(int[] arr, int parent, int length) {
int temp = arr[parent];
int lChild = 2 * parent + 1;
while (lChild < length) {
int rChild = lChild + 1;
if (rChild < length && arr[lChild] < arr[rChild]) {
lChild++;
}
if (temp >= arr[lChild]) {
break;
}
arr[parent] = arr[lChild];
parent = lChild;
lChild = 2 * lChild + 1;
}
arr[parent] = temp;
}
}