1. 类与对象

(1)编程是为了把现实世界的事物用编程语言描述来实现信息化。
(2)现实世界事物是如何表达的呢?

属性(外在特征) + 行为(内在行为)

(3)OO(Object–Oriented )面向对象是基于面向过程的一种编程思想。

对象:要研究的任何事物。
对象由数据(描述事物的属性)和作用于数据的操作(体现事物的行为)构成一独立整体。
从程序设计者来看,对象是一个程序模块,
从用户来看,对象为他们提供所希望的行为。在对内的操作通常称为方法。

类:类是对象的模板,是一组相关的属性和行为的集合。
即类是对一组有相同数据和相同操作的对象的定义,一个类所包含的方法和数据描述一组对象的共同属性和行为。

类是在对象之上的抽象,对象则是类的具体化,是类的实例。
类可有其子类,也可有其它类,形成类层次结构。

举例
学生----学生类;
张三----是类中的一个具体对象

面向对象开发:就是不断的创建对象,使用对象,指挥对象做事情。
面向对象设计:其实就是在管理和维护对象之间的关系。

面向对象特征:封装(encapsulation)、继承(inheritance)、多态(polymorphism)

2. 类的组成

(1)成员变量:就是事物的属性;
其实就是变量,只不过定义在类中,方法外,并且可以不用初始化。

(2)成员方法:就是事物的行为;
其实就是方法,只不过不需要static了

(3)案例:人类
定义类(声明类)实际就是定义类的静态属性和动态属性(方法)。
用户定义一个类实际上就是定义一个新的抽象数据类型。
使用类之前,必须先定义它,然后才可利用所定义的类来声明相应的变量,并创建对象。

[类修饰符] class 类名称 {  
     [修饰符] 数据类型 变量名;//声明成员变量
     [修饰符] 返回值类型 方法名(参数表){} //声明成员方法             
}
public class Person {
    public String name;
    public int age;
    public void show() {
        System.out.println("name:" + name + ", age:" + age);
    }
}

3. 对象的创建与使用

(1)创建对象

格式:类名 对象名 = new 类名();

(2)使用成员

成员变量:对象名.变量名;
成员方法:对象名.方法名(…);

可以将对象理解为一种新型的变量。
对象之间靠互相传递消息而相互作用,消息传递的结果是启动方法,完成一些行为或者修改接受消息的对象的属性。

对象完成工作后,将被销毁,所占用的资源将被系统回收。
一个对象的生命周期:创建 -> 使用 -> 销毁

class Person {
    public String name;
    public int age;
    public void show() {
        System.out.println("name:" + name + ", age:" + age);
    }
}
public class Test2 {
    public static void main(String[] args) {
        Person p = new Person();
        p.age = 13;
        p.name = "AAA";
        p.show();
    }
}

4. 成员变量和局部变量的区别

成员变量和局部变量的区别
在类中的位置不同:成员变量----在类中方法外,局部变量----方法内或者方法声明上
在内存中的位置不同:成员变量----堆内存,局部变量----栈内存
生命周期不同
成员变量----随着对象的存在而存在,随着对象的消失而消失
局部变量----随着方法的调用而存在,随着方法的调用完毕而消失
初始化值不同
成员变量----有默认的初始化值
局部变量----没有默认的初始化值,必须先定义,赋值,才能使用。
注意:如果有同名的变量,一般会采用就近原则。

5. 形式参数问题

(1)基本类型:基本类型作为形式参数,需要的是该基本类型的值。
(2)引用类型:引用类型作为形式参数,需要的是该引用类型的地址值。(对象)

6. 匿名对象

当一个对象被创建之后,在调用该对象的方法时,也可以不定义对象的引用变量,而直接调用这个对象的方法,这样的对象叫做匿名对象。

例如,若将

Person p = new Person();

p.show();

改写为:

new Person().show();

则Person()就是匿名对象。

(1)匿名对象:没有名字的对象;是对象的简化书写方式。
(2) 以使用匿名对象通常有如下两种情况:

A:如果对一个对象只需要进行一次方法调用。
B:将匿名对象做为实参传递给一个方法调用。
例:一个程序中有一个getSomeOne()方法要接收一个MyClass类对象作为参数,方法的定义如下:
public static void getSomeOne (MyClass c) { … }
可以用下面的语句调用这个方法。
getSomeOne(new MyClass( ) );

7. 封装

(1)隐藏实现细节,提供公共的访问方式
(2)好处:

A:隐藏实现细节,提供公共的访问方式
B:提高了代码的复用性
C:提高了代码的安全性

(3)使用原则

A:把成员变量隐藏
B:给出该成员变量对应的公共访问方式

8. 类型修饰符,如private关键字

类修饰符包含访问控制修饰符(只允许公共修饰符public和默认修饰符default两种)、抽象类修饰符abstract、最终类修饰符final。这里,abstract和final不能同时修饰一个类。
成员变量的访问权限修饰符public、protected、缺省和private
public修饰的成员变量完全公开,没有任何限制,可被任何程序包中的类访问;
protected修饰的成员变量可被类自身、子类、同一包中的类访问;
成员变量之前没有显示声明访问权限的,即为缺省访问控制符,可被类自身和同一包中的类或子类访问;
private修饰的成员变量只能被本类访问。

类的成员声明前加上私有访问控制符private,则成员只能被该类自身访问和修改,而不能被其他类(包括该类的子类)访问,从而达到了对数据最高级别保护的目的。

类的成员声明前加上公共访问控制符public,则表示该成员可以被其他类所访问。
造成安全性和数据封装性的下降,所以一般减少该成员的使用。

(1)是一个权限修饰符
(2)可以修饰类的成员(成员变量和成员方法)
(3)被private修饰的成员只在本类中才能访问。
(4)标准代码:

class Student {
	private String name;
	private int age;
	public void setName(String n) { name = n; }
	public String getName() { return name; }
	public void setAge(int a) { age = a; }
	public int getAge() { return age; }
	public void study() {}
}

9. this关键字

(1)this:代表本类的对象

方法被哪个对象调用,this就代表那个对象

(2)应用场景:

解决了局部变量隐藏成员变量的问题。
其他用法和super一起讲。

(3)标准代码:

class Student {
	private String name;  // 可以自动生成 get/set方法
	private int age;

	public String getName() { return name; }
	public void setName(String name) { this.name = name; }
	public int getAge() { return age; }
	public void setAge(int age) { this.age = age; }
	public void show() {
		System.out.println("[name:" + name + ", age:" + age + "]");
	}
}
public class Test {
	public static void main(String[] args) {
		Student s1 = new Student();
		s1.setName("BBB");
		s1.setAge(14);
		s1.show();
	}
}

10. static关键字

可以修饰成员变量和成员方法

用static修饰的成员变量称为“静态变量”,静态变量也称为类变量。
静态变量是隶属于类的变量,而不是属于任何一个类的具体对象。
在类定义中如果成员变量或成员方法没有用static来修饰,则该成员就是实例成员。

对于某类的任何一个具体对象而言,静态变量是一个公共的存储单元。
对于某类的任一对象访问静态变量访问它时,取到的都是相同数值;同样,任一对象修改它也是在同一内存单元做操作。

用static修饰的方法是属于类的静态方法(类方法)。
非static的方法是属于某个对象的方法,在该对象创建时,对象的方法在内存中拥有属于自己专用的代码段;而static的方法是属于整个类的,它在内存中的代码段将被所有对象所共用。
static方法只能访问static成员变量或static方法。
在静态方法中不能使用this或super。

static关键字特点

随着类的加载而加载
优先于对象存在
被类的所有对象共享(这也是我们判断是否使用静态关键字的条件)
可以通过类名调用

static关键字注意事项

在静态方法中是没有this关键字的
先进内存的不能访问后进内存的。反之可以。
静态方法只能访问静态的成员变量和静态的成员方法
简记:静态只能访问静态

所属不同

静态变量属于类,所以也称为为类变量
成员变量属于对象,所以也称为实例变量(对象变量)

内存中位置不同

静态变量存储于方法区的静态区
成员变量存储于堆内存

内存出现时间不同

静态变量随着类的加载而加载,随着类的消失而消失
成员变量随着对象的创建而存在,随着对象的消失而消失

调用不同

静态变量可以通过类名调用,也可以通过对象调用,成员变量只能通过对象名调用
public static void main(String[] args) {}
public 被jvm调用,访问权限足够大。
static 被jvm调用,不用创建对象,直接类名访问
void 被 jvm调用,不需要给jvm返回值
main 一个通用的名称,虽然不是关键字,但是被jvm识别
String[] args 以前用于接收键盘录入的

之前大家一直疑惑的一个问题:main方法的访问权限为何必须为public static?

由于JVM需要在类外调用main方法,而且JVM运行时相同在开始执行一个程序前,并没有创建main方法所在的类的一个实例对象,所以它只能通过类名来调用main方法作为程序的入口,因而该方法必须是static。

11. 构造方法

概述:给对象的数据进行初始化
构造方法格式

方法名与类名相同
没有返回值类型,连void都没有
没有具体的返回值

构造方法一般都是public,因为它们在创建对象时,是在类的外部被系统自动调用的。
构造函数若被声明为private,则无法在构造方法所在的类以外的地方被调用,但在该类的内部还是可以被调用。

注意事项

如果省略构造方法,Java编译器会自动为该类生成一个默认的构造方法,程序在创建对象时会自动调用默认的构造方法。
默认的构造方法没有参数,在其方法体中也没有任何代码,即什么也不做。
若class前面有public修饰符,则默认的构造方法前面也是public。
一旦用户为某类定义了构造方法,系统就不再提供默认的构造方法,这是Java的覆盖所致。

简单说

如果你不提供构造方法,系统会给出默认构造方法
如果你提供了构造方法,系统将不再提供
构造方法也是可以重载的

class Person {
	public String name;
	public int age;

	public Person() { // 无参构造
		System.out.println("Person()");
	}

	public Person(String _name, int _age) { // 有参构造
		name = _name;
		age = _age;
		System.out.println("Person(String _name, int _age)");
	}

	public void show() {
		System.out.println("[name:" + name + ", age:" + age + "]");
	}
}

public class Test1 {
	public static void main(String[] args) {
		System.out.println("input: ");

		Person p1 = new Person(); // 新建对象
		p1.name = "AAA";
		p1.age = 13;
		p1.show();

		Person p2 = new Person("BBB", 14);
		p2.show();

		new Person("CCC", 13).show(); // 匿名对象
		display(new Person("DDD", 14));
	}

	private static void display(Person p) {
		p.show();
	}
}

案例练习:【例1】圆柱体

需求:

  1. 定义圆柱体类,设定数据私有化,并通过Constructor构造函数完成赋值
  2. 使用static记录圆柱体数量
  3. 实现圆柱体底面积、体积的计算方法
import java.util.Scanner;

public class Main {
    public static void main(String[] args) throws Exception {
        Cylinder c1 = new Cylinder(2.5, 5);
        c1.count();

        System.out.println("volume : " + c1.volume());

        Cylinder c2 = new Cylinder(1.0, 2);
        c2.count();
        System.out.println("volme : " + c2.volume());
    }
}

class Cylinder {
    private static int num = 0;
    private static double pi = 3.14;
    private double radius;
    private double height;

    Cylinder(double r, double h) {
        this.radius = r;
        this.height = h;
        num++;
    }

    public void count() {
        System.out.println("create the number of Cylinder: " + num);
    }

    public double area() {
        return pi * radius * height;
    }

    double volume() {
        return area() * height;
    }
}

案例练习:【例2】员工信息

需求:

  1. 定义员工类、设定数据私有化、并提供get/set方法
  2. 提供Constructor构造方法
  3. 使用static记录员工数量
  4. test01():使用set对元素进行赋值
  5. test02():使用构造函数、对对象数组进行赋值
import java.util.Scanner;

public class Main {
    public static void test01() {
        Employees e1 = new Employees();
        e1.setId(1);
        e1.setName("AAAA");
        e1.setAge(18);
        e1.setSalary(3000.0);
        e1.show();

        Employees e2 = new Employees(2, "BBB", 23, 5000.0);
        e2.show();
        System.out.println("the number of emplyees : " + Employees.num);
    }

    public static void test02() {
        Employees[] es = new Employees[5];
        String[] name = { "A", "B", "C", "D", "E" };
        for (int i = 0; i < 5; i++) {
            es[i] = new Employees(i, name[i], (int) (Math.random() * 100 + 1), Math.random() * 10000);
            System.out.println("the number of emplyees : " + Employees.num);

        }

        for (int i = 0; i < 5; i++) {
            es[i].show();
        }
    }

    public static void main(String[] args) {
        test01();
        test02();
    }
}

class Employees {
    private int id; // 员工编号
    private String name;
    private int age;
    private double salary; // 薪水
    public static int num = 0;

    public int getId() {
        return id;
    }

    public void setId(int id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }

    public double getSalary() {
        return salary;
    }

    public void setSalary(double salary) {
        this.salary = salary;
    }

    public Employees() {
        ++num;
    }

    public Employees(int id, String name, int age, double salary) {
        this.id = id;
        this.name = name;
        this.age = age;
        this.salary = salary;
        ++num;
    }

    public void show() {
        System.out.println("id  :" + id);
        System.out.println("name:" + name);
        System.out.println("age :" + age);
        System.out.println("salary:" + salary);
        System.out.println("-------------------");
    }
}

12. 代码块

在Java中,使用 { } 括起来的代码被称为代码块,
根据其位置和声明的不同,可以分为:
局部代码块,构造代码块,静态代码块,同步代码块(多线程讲解)。

局部代码块:

在方法中出现;
限定变量生命周期,及早释放,提高内存利用率

构造代码块:

在类中方法外出现;
多个构造方法方法中相同的代码存放到一起,每次调用构造都执行,并且在构造方法前执行

静态代码块:

在类中方法外出现,并加上static修饰;
用于给类进行初始化,在加载的时候就执行,并且值执行一次。

class Student {
	static {
		System.out.println("静态代码块");//1
	}

	{
		System.out.println("构造代码块");//2
	}

	public Student() {
		System.out.println("构造方法");//3
	}
}

class Test {
	public static void main(String[] args) {
		Student s = new Student();
		//1,2,3 是输出的先后顺序
	}
}

上述代码执行流程

A:加载Student.class文件进内存
B:在栈中为s开辟空间
C:在堆中为学生对象开辟空间
D:为学生对象的成员变量赋默认值
E:为学生对象的成员变量赋显示值
F:通过构造方法给成员变量赋值
G:对象构造完毕,把地址赋值给s变量

13. 垃圾回收

垃圾回收(Garbage-collection)是Java语言提供的一种自动内存回收功能,可以让程序员减轻许多内存管理的负担,也减少程序员犯错的机会。

当一个对象被创建时,JVM会为该对象分配一定的内存、调用该对象的构造方法并开始跟踪该对象。当该对象停止使用时,JVM将通过垃圾回收器回收该对象所占用的内存。

Java是如何知道一个对象无用呢?
系统中的任何对象都有一个引用计数器来计数。

垃圾回收的好处:

把程序员从复杂的内存追踪、检测和释放等工作解放出来;
防止 了系统内存被非法释放,从而使系统更稳定。

垃圾回收的特点:

只有当一个对象不被任何引用类型的变量使用时,它的内存才可能被垃圾回收器回收;
不能通过程序强迫回收器立即执行;
当垃圾回收器将要释放无用对象的内存时,先调用该对象的finalze()方法。

14. Math类

Math包含用于执行基本数学运算的方法
Math类特点:没有构造方法,因为成员都是静态的
Math类获取随机数
(1)获取1-100之间的随机数
(2)猜数字小游戏

(1)获取1-100之间的随机数

class Test{
	public static void main(String[] args) {
		int num = (int)(Math.random()*100)+1;
		System.out.println(num);
	}
}

(2)猜数字小游戏

import java.util.Scanner;

class Test{
	public static void main(String[] args) {
		Scanner sc = new Scanner(System.in);
		int num = (int)(Math.random()*100)+1;//1~100
		boolean flag = true;

		do{
			System.out.println("请输入你认为的那个数字:");
			int num_t = sc.nextInt();
			if(num > num_t){
				System.out.println("太小了呢!");
			}else if(num < num_t){
				System.out.println("有点大哦!");
			}else{
				System.out.println("恭喜你,猜对了!");
				flag = false;
			}
		}while(flag);
	}
}

15. 制作帮助文档

(1)写代码
(2)加文档注释
(3)通过javadoc工具生成说明书
(4)javadoc -d 目录 -author -version ArrayTool.java

详情可查看【JAVA说明书的制作】

Logo

有“AI”的1024 = 2048,欢迎大家加入2048 AI社区

更多推荐