标签:引用 外部类 common 转型 图片 tps 写代码 封装 ble
概述
面向对象编程思想
? 面向对象编程思想就是,将真实世界的复杂关系,抽象为一个个对象,然后由对象之间的分工与合作,完成对真实世界的模拟。(总而言之,就是找对象做事儿)
明确需求
划分对象
对象的功能
对象之间的关系
面向对象编程的特点
封装
:封装(encapsulation)就是隐藏对象的属性和实现细节,仅对外公开接口,控制在程序中属性的读取和修改的访问级别 。继承
: 继承( inheritance)指的是 子类与父类的关系,子类可以继承父类中的属性和方法多态
: 多态(Polymorphism)按字面的意思就是“多种状态”。在面向对象语言中,接口的多种不同的实现方式即为多态。关于对象的三大特征,后续会逐渐展开讲解。
上述讲到,要面向对象编程,就得找对象做事儿。
找对象的前提,得先有对象。
现在没有对象怎么办?
那就得先创建对象,创建对象的规则,需要先知道如何定义类
类
比如,“狗”,“狗”是类,不是一个具体的对象,而是一个抽象的名称或概念,泛指世界上“会汪汪叫”、“对主人忠诚”、"会看家护院"、“爱啃骨头”、“有四条腿、两只眼睛、一个鼻子、两只耳朵等”具有这一系列特征的物种的称呼。
所以,类,简而言之就是一个抽象的概念;
对象
类与对象的关系
定义类
关键字:class
定义格式:
public class 类名 {
// 成员变量-描述对象的属性
// 成员方法-描述对象的方法
}
代码演示:
/* 定义类 */
public class Dog {
// 成员变量
String name;
String type;
String color;
// 成员方法
public void eat(){
System.out.println("我喜欢啃骨头");
}
public void sound(){
System.out.println("汪汪~~~");
}
}
注意:类名单词的首字母要大写(比如:Dog
)
创建和使用对象
关键字:new
创建格式:类名 对象名 = new 类名()
使用对象:
对象名.成员变量
对象名.成员变量=值
对象名.成员方法()
代码:
public class DogTest {
public static void main(String[] args) {
// 创建对象
Dog wangCai = new Dog();
// 设置对象的属性-成员变量
wangCai.name = "旺财";
wangCai.color = "黄色";
wangCai.type = "中华田园犬";
// 读取对象的属性
System.out.println("这一条狗的名字:" + wangCai.name);
System.out.println("这一条狗狗的毛色:" + wangCai.color);
System.out.println("这一条狗狗的种族:" + wangCai.type);
// 调用对象的方法
wangCai.eat();
wangCai.sound();
}
}
注意:
默认值:
代码:
public class DogTest02 {
public static void main(String[] args) {
Dog wangCai = new Dog();
// 读取对象的属性
System.out.println("这一条狗的名字:" + wangCai.name); // null
System.out.println("这一条狗狗的毛色:" + wangCai.color); // null
System.out.println("这一条狗狗的种族:" + wangCai.type); // null
}
}
// 字符串是引用数据类型,索引默认值是null
外
的变量。内
的变量。一个对象创建并为属性赋值的内存图
Person类代码
public class Person {
// 成员变量
String name;
int age;
// 成员方法
public void eat(){
System.out.println("吃饭");
}
}
PersonTest类代码
public class PersonTest {
public static void main(String[] args) {
Person zs = new Person();
zs.name = "张三";
zs.age = 10;
}
}
内存图解
总结:
一个对象调用方法的内存图
Person类代码-同上
PersonTest类代码
public class PersonTest {
public static void main(String[] args) {
Person zs = new Person();
zs.name = "张三";
zs.age = 10;
// 调用方法
zs.eat();
}
}
内存图解
总结
两个对象调用方法的内存图
Person类代码-同上
PersonTest类代码
public class PersonTest {
public static void main(String[] args) {
Person zs = new Person();
zs.name = "张三";
zs.age = 10;
zs.eat();
Person ls = new Person();
ls.name = "李四";
ls.age = 11;
ls.eat();
}
}
内存图解
总结
? 封装(encapsulation)就是 隐藏对象的属性和实现细节,仅对外公开接口
,控制在程序中属性的读取和修改的访问级别 。
? 封装的可以让代码更加健壮且易于维护,提高程序的安全性。
private关键字修饰成员变量
private 数据类型 成员变量名;
对外提供公开的getXXX/setXXX方法操作对象的属性。
代码:
public class Person {
private String name;
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;
}
}
什么是构造方法-construction
与类同名的方法
方法修饰没有返回值类型,没有void。
public class Person{
// 无参构造方法
public Person(){
}
}
注意:类默认有一个无参的构造方法。构造方法可重载
构造方法的作用
代码:
Person类
public class Person {
private String name;
private int age;
// 无参数构造方法
public Person() {
}
// 有参数构造方法
public Person(String name, int age) {
this.name = name;
this.age = age;
}
public void show(){
System.out.println("姓名:" + this.name);
System.out.println("年龄:" + this.age);
}
}
测试类
public class PersonTest {
public static void main(String[] args) {
// 【调用无参构造方法】
Person zs = new Person();
zs.name = "张三";
zs.age = 10;
zs.show(); // 打印结果:姓名:张三 年龄:10
// 【调用有参构造方法】
Person ls = new Person("李四",12);
ls.show(); // 打印结果:姓名:李四 年龄:12
}
}
? JavaBean 是 Java语言编写类的一种标准规范。符合 JavaBean 的类,要求类必须是具体的和公共的,并且具有无参数的构造方法,提供用来操作成员变量的 set 和 get 方法。
public class 类名 {
// 成员变量
// 无参构造方法【必须】
// 有参构造方法
// get/set方法
// 成员方法
}
什么是继承?
继承是子类和父类的关系,子类可以使用父类中的成员。
例如:现实生活中的继承
注意:
Java的继承是单继承,但支持多层继承。
所有的类都直接或间接的继承了Object类
对象 instanceof类
检测一个对象是否属于某个类。返回布尔值,true表示属于,false表示不属于。
Person类
public class Person {
}
PersonTest类
public class PersonTest {
public static void main(String[] args) {
Person p1 = new Person();
// p1属于Person类
System.out.println(p1 instanceof Person); // 结果:true
// p1也属于Object类
System.out.println(p1 instanceof Object); // 结果:true
}
}
继承的作用
关键字:extends
格式
public class 子类 extends 父类 {
}
代码:
父类-手机类
public class Phone {
private String name;
private int year;
public Phone() {
}
public Phone(String name, int year) {
this.name = name;
this.year = year;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getYear() {
return year;
}
public void setYear(int year) {
this.year = year;
}
// 打电话功能
public void call(){
System.out.println("打电话");
}
// 发短信
public void sendMessage(){
System.out.println("发送文字");
}
// 手机信息
public void showInfo(){
System.out.println("手机名称:" + this.name);
System.out.println("生产年份:" + this.year);
}
}
子类-智能手机类
/*智能手机类*/
public class IntelligentPhone extends Phone {
public IntelligentPhone() {
}
public IntelligentPhone(String name, int year) {
super(name, year);
}
public void playMusic(){
System.out.println("播放音乐");
}
}
测试类
public class Test {
public static void main(String[] args) {
IntelligentPhone iphone = new IntelligentPhone("iphone100",2100);
iphone.call(); // 打电话
iphone.sendMessage(); // 发送文字
iphone.playMusic(); // 播放音乐
iphone.showInfo(); // 手机名称:iphone100 生产年份:2100
}
}
关键字:super
,在子类中表示父类的引用。
super(参数列表)
super.成员变量名
super.成员方法()
子类中的方法和父类中的方法重名时(返回值和参数列表一致),叫做方法的重载
代码:
父类-同上手机类
子类
public class IntelligentPhone extends Phone {
public IntelligentPhone() {
}
public IntelligentPhone(String name, int year) {
super(name, year);
}
public void playMusic(){
System.out.println("播放音乐");
}
@Override
// 重写父类的方法sendMessage
public void sendMessage() {
// 调用父类的发送文字的功能
super.sendMessage();
// 扩展发送图片
System.out.println("发送图片");
}
}
测试类
public class Test {
public static void main(String[] args) {
IntelligentPhone iphone = new IntelligentPhone("iphone100",2100);
iphone.sendMessage();
}
}
// 结果:
// 发送文字
// 发送图片
抽象类和抽象方法的定义
abstract
public abstract 返回值类型 方法名(参数列表);
public abstract class 类名{}
什么时候适合使用抽象方法
当不同子类有相同的行为,但又有不同的具体实现时,此时父类中定义方法时仅定义声明即可。
代码:需求-创建一条狗对象和一只猫对象,它们有不同的叫声
父类-Animal
public abstract class Animal {
private String name;
private int age;
public Animal() {};
public Animal(String name, int age) {
this.name = name;
this.age = age;
}
public void sleep(){
System.out.println("睡觉~~~");
}
// 【抽象方法】不同的动物,叫声,所以让子类重写具体的方法体
public abstract void shout();
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;
}
}
子类-Cat
public class Cat extends Animal {
public Cat(){}
public Cat(String name,int age){
super(name,age);
}
@Override
public void shout() {
System.out.println(this.getName() + ":喵喵~~~");
}
}
子类-Dog
public class Dog extends Animal {
public Dog(){};
public Dog(String name,int age){
super(name,age);
}
@Override
public void shout() {
System.out.println(this.getName() + ":汪汪~~~");
}
}
测试类-Test
public class Test {
public static void main(String[] args) {
Cat cat = new Cat("汤姆",2);
cat.shout(); //结果: 汤姆:喵喵~~
Dog dog = new Dog("旺财",3);
dog.shout(); // 结果: 旺财:汪汪~~
}
}
概述
接口的定义和实现
格式:
定义接口
public interface 接口名称{
// 【抽象方法】
public abstract 返回数据类型 抽象方法名(参数列表);
// 可简写为: 返回数据类型 抽象方法名(参数列表);
// 【默认方法】
public default 返回数据类型 方法名(){
// 方法体
}
// 【静态方法】
public static 返回数据类型 方法名(){
// 方法体
}
// 【私有方法】
private 返回数据类型 方法名(){
// 方法体
}
}
实现接口:
public class 实现类名 implements 接口1,接口2...接口n {
// 重写接口中的抽象方法【必须】
// 重写接口中的默认方法【可选】
}
接口可以继承其他接口
public interface 接口1 extends 接口2,接口3...接口n{
}
注意:
代码:
接口
public interface CommonInterface {
// 常量
public final double VERSION = 1.0;
// 抽象方法
public abstract void fly();
// 默认方法
public default void fn(){
fn1();
System.out.println("默认方法");
}
// 私有方法
private void fn1(){
System.out.println("私有方法");
}
// 静态方法
public static void show(){
System.out.println("静态方法");
}
}
实现类
public class Bird implements CommonInterface {
@Override
public void fly() {
System.out.println("展开翅膀飞行");
}
}
测试类
public class Test {
public static void main(String[] args) {
Bird xn = new Bird();
xn.fly();
xn.fn();
}
}
接口和抽象类的区别?
什么场景下用继承类?什么场景下用实现接口?
若强调多个类是什么时,可以使用继承。
若强调多个类能做什么时,可以使用实现接口。
多态Polymorphism,按字面意思就是“多种状态”。
在面向对象语言中,接口的多种不同的实现方式即为多态 。
多态性是允许你将父对象设置成为一个或更多的他的子对象相等的技术,赋值之后,父对象就可以根据当前赋值给它的子对象的特性以不同的方式运作(摘自“Delphi4?编程技术内幕”)。
简单的说,就是一句话:允许将子类类型的指针赋值给父类类型的指针。
把不同的子类对象都当作父类来看,可以屏蔽不同子类对象之间的差异,写出通用的代码,做出通用的编程,以适应需求的不断变化。
实现多态的前提条件
实现方式
格式:父类或被实现的接口 变量名 = new 子类或实现类()
代码:
父类-Animal
public abstract class Animal {
private String name;
private String type;
public Animal(){}
public Animal(String name,String type){
this.name = name;
this.type = type;
}
public abstract void sound();
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getType() {
return type;
}
public void setType(String type) {
this.type = type;
}
}
子类-Bird
public class Bird extends Animal {
public Bird(){}
public Bird(String name,String type) {
super(name,type);
}
@Override
public void sound() {
System.out.println(this.getName() + ":叽叽喳喳~~");
}
}
子类-Dog
public class Dog extends Animal {
public Dog(){}
public Dog(String name,String type) {
super(name,type);
}
@Override
public void sound() {
System.out.println(this.getName() + ":汪汪~~~");
}
public void play(){
System.out.println("狗狗跳起来接飞盘!");
}
}
测试类-Test
public class Test {
public static void main(String[] args) {
AnimalSound(new Dog("旺财","中华田园犬")); // 旺财:汪汪~~~
AnimalSound(new Bird("小咕","麻雀")); // 小咕:叽叽喳喳~~
}
// 动物的叫声
public static void AnimalSound(Animal animal){
animal.sound();
}
}
还是上述代码,若让一个Dog对象指向父类的引用,再调用Dog的play方法时,会编译出错!
代码
public class Test2 {
public static void main(String[] args) {
Animal animal = new Dog("旺财","中华田园犬");
// animal.play(); // 编译不通过
}
}
此时我们可以通过向下转型为Dog对象,实现对象Dog对象独有的方法调用。
父类/接口 父类引用 = new 子类/实现类()
(子类或实现类)父类引用
代码如下:
public class Test2 {
public static void main(String[] args) {
Animal animal = new Dog("旺财","中华田园犬"); // 向上转型
((Dog) animal).play(); // 狗狗跳起来接飞盘! // 向下转型
}
}
注意:
向下转型时,若子类不对应,在运行时,会出现ClassCastException异常!
可以通过instanceOf方法检测。
public class Test2 {
public static void main(String[] args) {
Animal animal = new Bird("小咕","麻雀");
// ((Dog) animal).play(); // ClassCastException 因为向上转型的子类对象不是Dog
//【正确方式,先验证类型,再调用】
if(animal instanceof Dog){
((Dog) animal).play();
}
}
}
若定义在父类中的某些成员变量或成员方法,不希望被子类修改,如何操作呢?
可以使用关键字final
修饰
概述
在Java中提供了四种访问权限,使用不同的访问权限修饰符修饰时,被修饰的内容会有不同的访问权限,
不同权限的访问能力
可见,public具有最大权限。private则是最小权限。
编写代码时,如果没有特殊的考虑,建议这样使用权限:
概述
内部类和外部类
:将一个类A定义在另一个类B里面,里面的那个类A就称为内部类,B则称为外部类。
内部类定义格式
class 外部类 {
class 内部类{ }
}
在描述事物时,若一个事物内部还包含其他事物,就可以使用内部类这种结构。比如,汽车类 Car 中包含发动机
类 Engine ,这时, Engine 就可以使用内部类来描述,定义在成员位置。
class Car {
//外部类
class Engine {
//内部类
}
}
访问特点
创建内部类对象
格式:外部类名.内部类名 对象名 = new 外部类型().new 内部类型()
;
人类
public class Person {
private boolean live = true;
class Heart {
public void jump() {
// 直接访问外部类成员
if (live) {
System.out.println("心脏在跳动");
} else {
System.out.println("心脏不跳了");
}
}
}
public boolean isLive() {
return live;
}
public void setLive(boolean live) {
this.live = live;
}
}
测试类
public class Test03 {
public static void main(String[] args) {
// 创建外部类对象
Person p = new Person();
// 创建内部类对象
Heart heart = p.new Heart();
// 调用内部类方法
heart.jump();
// 调用外部类方法
p.setLive(false);
// 调用内部类方法
heart.jump();
}
}
// 输出结果: 心脏在跳动 心脏不跳了
内部类仍然是一个独立的类,在编译之后会内部类会被编译成独立的.class文件,但是前面冠以外部类的类名
和$
符号 。 比如,Person$Heart.class
匿名内部类介绍
匿名内部类 :是内部类的简化写法。它的本质是一个 带具体实现的 父类或者父接口的 匿名的 子类对象。
开发中,最常用到的内部类就是匿名内部类了。以接口举例,当你使用一个接口时,似乎得做如下几步操作,
我们的目的,最终只是为了调用方法,那么能不能简化一下,把以上四步合成一步呢?匿名内部类就是做这样的快
捷方式。
匿名内部类的使用
前提:匿名内部类必须继承一个父类或者实现一个父接口。
格式
new 父类名或者接口名(){
// 方法重写
@Override
public void method() {
// 执行语句
}
};
代码
Fly接口
public interface Fly {
void fly();
}
测试类
public class Test {
public static void main(String[] args) {
/*
1.等号右边:是匿名内部类,定义并创建该接口的子类对象
2.等号左边:是多态赋值,接口类型引用指向子类对象
*/
Fly bird = new Fly() {
@Override
public void fly() {
System.out.println("小鸟飞...");
}
};
// 调用匿名内部类重写后的方法。
bird.fly();
}
}
匿名内部类的作用
概述
关于 static 关键字的使用,它可以用来修饰的成员变量和成员方法,被修饰的成员是属于类的,而不是单单是属
于某个对象的。也就是说,既然属于类,就可以不靠创建对象来调用了。
类变量
当 static 修饰成员变量时,该变量称为类变量。该类的每个对象都共享同一个类变量的值。任何对象都可以更改
该类变量的值,但也可以在不创建该类的对象的情况下对类变量进行操作。
修饰符 static 数据类型 变量名;
修饰符 static int age
静态方法
当 static 修饰成员方法时,该方法称为类方法 。静态方法在声明中有 static ,建议使用类名来调用,而不需要
创建类的对象。调用方式非常简单。
定义格式:static 返回值类型 方法名(参数列表){}
代码:
public static void show(){
System.out.println("hello");
}
注意事项:
静态代码块
static{}
public class ClassName{
static {
// 执行语句
}
}
总结
static 关键字,可以修饰变量、方法和代码块。在使用的过程中,其主要目的还是想在不创建对象的情况
下,去调用方法。下
标签:引用 外部类 common 转型 图片 tps 写代码 封装 ble
原文地址:https://www.cnblogs.com/lpl666/p/11980012.html