Java入门知识
Java概念知识
Java 面向对象的四大特性
封装 抽象 继承 多态
JDK运行环境
-
编译 --------》 Javac.exe
-
运行---------》 Java.exe
-
编写的代码要放在 .java 后缀名的文件中
-
取类名最好与文件名相同,因为生成的 .class 文件是以类名为文件名的
-
jdk 的运行程序(Javac和Java)需要配置环境变量才能在任意目录运行Java代码
我的第一段Java代码
class Myfirst{
public static void main(String[] args){
System.out.println("hello java");
}
}
Java程序固定格式
- public :一种权限修饰符,还有private,protected等
- static :一种静态修饰符
- void :返回值,表示没有返回值
- main :主函数名,名称固定
- String [] args :数组类型参数
- System.out.println :写Java程序无非就是写类,类创建出对象来使用,完成某些功能就是通过类来实现;System 是我们Java中已经定义好的类可以直接使用
- println (); :方法,接受一个参数,参数可以是多种类型
Java 单词划分
-
关键字(保留字)
-
标识符:a-z ,A-Z ,0-9 ,_ ,$
- 类名:开头字母需要大写
- 严格区分大小写
- 并且不能以数字开头;
一、常量与变量
常量:值不能改变
变量:值能改变
-
格式
- 数据类型 变量名;
- 数据类型 变量名 = 变量值; 分类和作用域
- 局部变量:定义在某个函数中的变量
- 全局变量:定义在类的变量
- 作用域:变量定义在哪一对最靠近的大括号中,就在这个大括号中有效
二、数据类型
基本数据类型(8种)
1. 整型
byte : 8位二进制 -128~127 (1个字节)
short :16位二进制 -32768~32767 (2个字节)
int(默认) :32位二进制 (4个字节)
long :64位二进制 (8个字节)
2. 浮点型
float : 表示32位浮点数 (4个字节)
double (默认): 表示64位浮点数 (8个字节)
3. 字符型
char :单引号' '里面只能有一个字符 (2个字节)
4. 布尔型
boolean (1个字节)
类型转换
自动类型转换
将取值范围小的类型 自动提升为 取值范围大的类型
转换规则
byte、short、char‐‐>int‐‐>long‐‐>float‐‐>double
int + float 是float类型
强制类型转换
将 取值范围大的类型 强制转换成 取值范围小的类型 。
把大的装到小的中 byte b = (byte)30000;
但会丢失精度
引用数据类型
- 对象类型 (Person p = new Person())
- 数组类型 (int [] a = new int [5])
三、运算符
- 算术运算符:+、-、*、/、%、++、- - (‘+’也可表示连接)
独立运算:
变量在独立运算时, 前++ 和 后++ 没有区别 。
变量 前++ :例如 ++i 。
变量 后++ :例如 i++ 。
混合运算:
和其他变量放在一起, 前++ 和 后++ 就产生了不同。
变量 前++ :变量a自己加1,将加1后的结果赋值给b,也就是说a先计算。
int a = 1;
int b = ++a;
System.out.println(a);//计算结果是2
System.out.println(b);//计算结果是2
变量 后++ :变量a先把自己的值1,赋值给变量b,此时变量b的值就是1,变量a自己再加1。
int a = 1;
int b = a++;
System.out.println(a);//计算结果是2
System.out.println(b);//计算结果是1
- 赋值运算符:=、+=、-=、*=、/=
同一个作用域不可以重复定义 - 关系运算符:<, > , <= , >= ,!= ,==
- 逻辑运算符:&& , || , !
- 三元运算符 : ? :
int a = 3;
int b = 5;
a>b?100:200;
?左边为真,就取:左边的值
?左边为假,就取:右边的值
拓展
byte b1=1;
byte b2=2;
byte b3=1 + 2;
byte b4=b1 + b2; //变量相加默认是 int 类型
System.out.println(b3);
System.out.println(b4);
分析: b3 = 1 + 2 , 1 和 2 是常量,为固定不变的数据,在编译的时候(编译器javac),已经确定了 1+2 的结果并没有超过byte类型的取值范围,可以赋值给变量 b3 ,因此 b3=1 + 2 是正确的。
反之, b4 = b1 + b2 , b1 和 b2 是变量,变量的值是可能变化的,在编译的时候,编译器javac不确定b1+b2的结果是什 么,因此会将结果以int类型进行处理,所以int类型不能赋值给byte类型,因此编译失败。
short s = 1;
s+=1;
System.out.println(s);
分析: s += 1 逻辑上看作是 s = s + 1 计算结果被提升为int类型,再向short类型赋值时发生错误,因为不能将取值范围 大的类型赋值到取值范围小的类型。但是, s=s+1进行两次运算 , += 是一个运算符,只运算一次,并带有强制转换的特点, 也就是说 s += 1 就是 s = (short)(s + 1) ,因此程序没有问题编译通过,运行结果是2.
四、修饰符
-
权限修饰符
访问权限 类 包 子类 其他包
public ∨ ∨ ∨ ∨
protect ∨ ∨ ∨ ×
default ∨ ∨ × ×
private ∨ × × ×
-
其他修饰符
static: 静态修饰符
final :可将变量变成常量
abstract:抽象修饰符
五、条件语句
if(条件){
//代码
};
if(条件){
//代码
}else{ ... }
if(条件){
//代码
}else if{
...
}else{...}
嵌套使用
switch(参数){
case vlaue:
//语句
break; //可选
case vlaue:
//语句
break; //可选
...
default:
//语句
}
参数类型只能为byte,short,int,char或String类型
case数量可以多个但是类型必须相同
break :结束选择结构
case下没有break (case的穿透性)
一直往下穿,直到遇到break或者程序执行完为止
六、循环语句
while(条件){
//代码块
}
do{
//代码块
}while(条件);
for(语句1;语句2;语句3){
//代码块
}
//语句1:初始化,只在开始执行一次赋值;
//语句2:条件判断,每次循环前先判断后执行代码块
//语句3:迭代语句,增加步长对参数进行一个改变
for(int x = 0; x < 10; x++) {
System.out.println("HelloWorld"+x);
}
for 和 while 的小区别:
控制条件语句所控制的那个变量,在for循环结束后,就不能再被访问到了,而while循环结束还可以继 续使用,如果你想继续使用,就用while,否则推荐使用for。
原因是for循环结束,该变量就从内存中消 失,能够提高内存的使用效率在已知循环次数的时候使用推荐使用for,循环次数未知的时推荐使用while。
break和continue
break:直接跳出整个循环
for (int i = 1; i<=10; i++) {
//需求:打印完两次HelloWorld之后结束循环
if(i == 3){
break;
}
System.out.println("HelloWorld"+i);
}
continue:跳出当前循环,继续执行下次循环
for (int i = 1; i <= 10; i++) {
//需求:不打印第三次HelloWorld
if(i == 3){
continue;
}
System.out.println("HelloWorld"+i);
}
嵌套使用
for(int i = 0; i < 5; i++){
for(int j = 0; j < 8; j++){
//不换行打印星号
System.out.print("*");
}
//内循环打印8个星号后,需要一次换行
System.out.println();
}
System.out.print() //print 表示打印,不带ln不会自动换行,后面输出的数据会跟在这句的后面。
System.out.println() //print表示打印,ln表示换行,后面数据的数据会在下一行中打印出。
System.out.printf(); //它表示格式化输出
System.out.printf("%f", d);// "f"表示格式化输出浮点数
七、函数
- 定义:在类中具有特定功能的独立小程序,也称为方法;
- 格式:
修饰符 返回值类型 函数名(参数类型 形式参数1,参数类型 形式参数2){
//函数体
return 返回值
}
- 函数调用:主函数虚拟机自动调用;自定义函数由主函数调用
函数名(); //没有参数时就这样调用
函数名(实际参数1,实际参数2,...);
- 静态函数不能调用非静态函数或字段;可用修饰符 static 对非静态进行修饰转化为静态
- 函数只能定义在类中,函数中不能定义函数,只能调用。
- 函数的重载:指在同一个类中,允许存在一个以上的同名方法,只要它们的参数列表不同即可,与修饰符和返 回值类型无关。
- 针对同一个类中的函数
- 函数同名不同参
- 不同参指个数不同,数据类型不同,顺序不同。
- 系统会根据参数的个数与类型自动匹配,决定调用哪个函数
- 主函数:
public static void main(String[] args)
- 一个类只有定义了主函数他才能独立的运行,因为主函数会被虚拟机自动执行
- 有很多个类,但拥有主函数的类才是程序的入口点
- 构造函数:
- 当一个对象被创建时,构造函数用来初始化该对象。构造函数和它所在类的名字相同,但构造函数没有返回值。
- 构造函数可以无参,也可以有参。
- 所有的类都有构造函数,Java会默认提供一个无参的构造函数,只是不显示。
- 一旦自己定义了构造函数,Java提供的默认构造函数就会失效,要想有一个无参的构造函数还得自己手动声明。
八、数组
int[] a;
a = new int [10];
//
int[] a=new int [10];
//
int[] arr = new int[]{1,2,3,4,5};
//
int[] a={100,200,300};
得到数组的大小:a.length
a.length 表示取得其中的一个属性
a.length() 表示取得其中的一个函数
索引访问数组中的元素:
- 数组名[索引]=数值,为数组中的元素赋值
- 变量=数组名[索引],获取出数组中的元素
//定义存储int类型数组,赋值元素1,2,3,4,5
int[] arr = {1,2,3,4,5};
//为0索引元素赋值为6
arr[0] = 6;
//获取数组0索引上的元素
int i = arr[0];
System.out.println(i);
数组异常:
- 越界异常:每个创建出来的数组长度都是固定的,不能访问超过其长度的空间。
- 空指针异常:
arr = null;
那么变量arr将不会在保存数组的内存地址。
数组作为方法参数和返回值:
- 数组作为方法参数传递,传递的参数是数组内存的地址。
- 数组作为方法的返回值,返回的是数组的内存地址。
如何使用Java提供的类:
1、导入包 import java.util.Arrays; //写在类上面
2、直接通过固定格式引用方法或属性 Arrays.sort(a); //将数组a里面的内容排序
九、类与对象
面向过程:以过程为中心的思想。
面向对象:以对象为中心的思想。
类:属性和方法
用来描述事物的特性通常有属性和方法两方面
这两方面在程序代码中的体现就是字段和函数
一个类中包括的是字段和函数
类和对象的关系:
类是对象的总称
对象是类的实例化,可通过关键字new来实例化
new Person(); //具体的某个人
class Person(); //声明了人的群体类
整个编程思路是:
无论做什么事情,首先想到类,然后实例化对象的这样一个过程。
因为做任何事都是通过对象中的属性或方法来实现的。 new Car().repair();
如果没有这样一个类,没有这样的方法,我们就自己手动写一个类,写一个方法来做这件事,这就是面向对象的开思想
如果这个类的属性或方法是静态的,我们就可以直接通过类名.属性或者类名.方法 就可以了
创建类的实例:
构造函数-------------通过new关键字创建对象
默认情况下,系统会给每个类提供一个默认的构造函数,无参的
public Person(){} //Person 类的无参构造函数(默认的没有显示出来)
//但就是通过构造函数才能创建对象,否则会报错
new Person(); //创建对象的话,说明这个隐形的构造函数存在
//创建一个 Person 类
public class Person{
//属性
private String name;
//方法
public void say(){
System.out.println("hello");
}
}
//创建一个 独立运行(主函数)的类
public class TestPerson{
public static void main(String [] args){
//System.out.println("hello java");
//new Person();
Person p;
p = new Person();
}
}
创建出的对象如何使用:创建对象实际在内存分配一个有地址的空间,我们只需用一个Person类型的变量来指向它就可以Person p; p = new Person();
错误: 无法将类 Person中的构造器 Person应用到给定类型;
p = new Person();
这就是构造函数的意义所在;由于系统提供的是无参的构造函数,所有创建的对象不可以有参数;
一旦我们自己写了构造函数public Person(String name){ }
系统的默认构造函数会失效,且我们创建对象时需要和我们自己写的构造函数参数保持一致。
创建出的对象,调用类中的属性与方法:
访问权限,如果属性或对象被private修饰了就无法调用;
错误: name 在 Person 中是 private 访问控制
System.out.println(p.name);
对象名.属性; //调用属性的值
对象名.方法名(参数); //调用类中的方法
private String name="Zhangsan";-------->public String name="Zhangsan";
在不改变访问权限情况下,如何拿到属性的值,并且我们还想要设置属性的值:
set ,get 方法:
//主函数类
public class TestPerson{
public static void main(String [] args){
//System.out.println("hello java");
//new Person();
Person p;
//p = new Person("zhangsan");
p = new Person();
p.setName("lisi");
System.out.println(p.getName());
//p.name="zhangsan";
}
}
//Person类
public class Person{
private String name="xiejun";
//通过get方法拿到private修饰的属性值
public String getName(){
return name;
}
//通过set方法修改private修饰的属性值
public void setName(String name){
this.name=name; //this.name this就代表当前类,this.name也就是我们类中的属性
} //左边的name代表private修饰的name,右边的name代表后面用户传来的值;
/*public Person(String name){
}*/
public void say(){
System.out.println("hello");
}
}
一般情况下,程序为了保护私有属性的安全性,不让外界随意访问,就会这样设置
如果设置有参的构造函数,就是为了给类中的属性一个默认值
public Person(String name){
this.name=name;
}
创建对象时可直接对属性赋值
p = new Person("zhangsan");