17

Java零基础系列教程10Java抽象与封装

 3 years ago
source link: https://segmentfault.com/a/1190000025184545
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.

配套视频教程

本文B站配套视频教程

软件出现的目的

用计算机的语言描述现实世界

用计算机解决现实世界的问题

为什么使用面向对象

世界由对象组成

面向对象的思想 描述 面向对象的世界 符合人类思维习惯

6biqA3e.png!mobile

从现实中抽象出类分三步:

  1. 找出它的种类
  2. 找出它的属性
  3. 找出它的行为

用面向对象描述世界

第一步:发现类

class Dog {

}

根据“对象”抽象出“类”

第二步:发现类的属性

狗类共有的特征:

  1. 品种
  2. 年龄
  3. 昵称
  4. 健康情况
  5. 跟主人的亲密度

… …

class Dog { 
    String name = "旺财"; // 昵称
    int health = 100; // 健康值    
    int love = 0;   // 亲密度
    String strain = "拉布拉多犬"; // 品种 
}

只放和业务相关的属性

第三步:发现类的方法

狗类共有的行为:

  1. 输出自己的信息

… …

class Dog { 
    String name = "旺财";   // 昵称
    int health = 100; // 健康值    
    int love = 0;     // 亲密度
    String strain = "拉布拉多犬"; // 品种 
    /* 输出狗的信息 */
    public void print() {
        // 输出狗信息的代码
    } 
}

只放和业务相关的方法

使用类图描述类

bYRJFvY.png!mobile

实践

实现领养宠物功能

编写宠物类Dog和Penguin

创建宠物对象,输入领养的宠物信息并输出

2mq2uy.png!mobile

bUNzA3.png!mobile

对象初始化

Penguin pgn = new Penguin();
pgn.name = "qq";
pgn.sex = "Q仔";

能否在创建对象的同时就完成赋值?

使用构造方法:

Penguin pgn1 = new Penguin();

class Penguin {
    // 属性
    /* 无参构造方法 */
    public Penguin() {
           name = "qq";
           love = 20;
           sex = "Q仔";
           System.out.println("执行构造方法");
    }
}

构造方法

vY7vEnf.png!mobile

系统提供默认无参构造方法

public Penguin() {

}

自定义构造方法

public Penguin () {
        name = "qq";
        love = 20;
        sex = "Q仔";
}
public Penguin (String name,int health,int love,String sex ) {
        this.name = name;
        this.health = health;
        this.love = love;
        this.sex = sex;
}

this关键字是对一个对象的默认引用,这里用以区分同名成员变量

方法重载

MNzuiyf.png!mobile

System.out.println(45);
System.out.println(true);
System.out.println("狗在玩耍!");

调用重载方法

pgn = new Penguin();
pgn.print();
pgn = new Penguin("美美", 80, 20, "Q仔");
pgn.print();

一个例子

class Penguin {
       String name = null; //昵称
       int health = 0; // 健康值
       String sex = null; // 性别
       public void Penguin() {    
               health=10;
               sex="雄";
               System.out.println("执行构造方法");
        }
        public void print() {
               System.out.println("企鹅的名字是" + name + ",健康值是" 
                                                 + health + ",性别是" + sex);
        }
}
Penguin pgn3= new Penguin();
pgn3.print();

2QBraiv.png!mobile

找出下面代码的问题

class Dog {
       private String name = "旺财";   // 昵称
       private int health = 100;  // 健康值    
       private int love = 0;     // 亲密度    
       public void play(int n) {
              int localv;
              health = health - n;        
              System.out.println(name+" "+ localv +" "+health+" "+love); 
       }
       public static void main(String[] args) {
              Dog d=new Dog();
              d.play(5);
       }
}

static静态成员

一个例子 统计对象被创建出来的个数

class Person
{
    public String name;
    public int age;
    static public long  all_count;
    public Person(){
        all_count++;
    }
    public Person( String name , int age ){
        all_count++;
        this.name = name;
        this.age = age;
    }
    // 统计人数的函数
    public long getCount(){
      return all_count;
    }
    // 应该具备找同龄人的功能
    public boolean isSameAge( Person p1 ){
      return this.age == p1.age;
    }
}
class Demo9 
{
    public static void main(String[] args) 
    {
        Person p1 = new Person( "jame" ,  34 );
        Person p2 = new Person( "lucy" ,  34 );

        Person p3 = new Person( "lili" ,  34 );
        Person p4 = new Person();
        System.out.println( p1.getCount() + " " + p2.getCount() + "  " + p3.getCount()  );
        System.out.println( p1.isSameAge( p2 ) );
        System.out.println( p1.isSameAge( p3 ) );
    }
}

4:static特点

1 随着类的加载而加载,静态会随着类的加载而加载,随着类的消失而消失。说明它的生命周期很长。

2 优先于对象存在。—>静态是先存在,对象是后存在。
     3 被所有实例(对象)所共享。
      4 可以直接被类名调用

67faUf3.png!mobile

使用static定义方法

用类名调用: Person.print();

静态方法只能访问静态属性,不能访问实例属性

找错误

class Dog {
       private String name = "旺财"; // 昵称
       private int health = 100;     // 健康值
       private int love = 0;        // 亲密度        
       public void play(int n) {
              static int localv=5;        
              health = health - n;        
              System.out.println(name+" "+localv+" "+health+" "+love);
       }    
       public static void main(String[] args) {
              Dog d=new Dog();
              d.play(5);
       }
}

封装

Dog d = new Dog();

d.health = -1000;

属性随意访问,不合理的赋值

封装的概念

封装:将类的某些信息隐藏在类内部,不允许外部程序直接访问,而是通过该类提供的方法来实现对隐藏信息的操作和访问

封装的好处

1.隐藏类的实现细节

2.只能通过规定方法访问数据

3.方便加入控制语句

4.方便修改实现

封装的步骤

ZFJ3m2f.png!mobile

class Dog {
    private String name = "旺财"; // 昵称
    private int health = 100; // 健康值
    private int love = 0;   // 亲密度
    private String strain = "拉布拉多犬"; // 品种
    public int getHealth() {
        return health;
    }
    public void setHealth (int health) {
        if (health > 100 || health < 0) {
            this.health = 40;
            System.out.println("健康值应该在0和100之间,默认值是40");
        } else
            this.health  =  health;
    }
    // 其它getter/setter方法
}

this

用类名定义一个变量(对象,实例)的时候,定义的只是一个引用,外面可以通过这个引用来访问这个类里面的属性和方法。

那么类里面是够也应该有一个引用来访问自己的属性和方法呢?

JAVA提供了一个很好的东西,就是 this 对象,它可以在类里面来引用这个类的属性和方法。

先来个简单的例子:

public class ThisDemo {  
    String name="Mick";
    public void print(String name){
        System.out.println("类中的属性 name="+this.name);
        System.out.println("局部传参的属性="+name);
    }   
    public static void main(String[] args) {
        ThisDemo tt=new ThisDemo();
        tt.print("Orson");
    }
}

关于返回类自身的引用,《Thinking in Java》有个很经典的例子。

通过this 这个关键字返回自身这个对象然后在一条语句里面实现多次的操作

public class ThisDemo {  
    int number;
    ThisDemo increment(){
         number++;
         return this;
    }  
  private void print(){
         System.out.println("number="+number);
    }
    public static void main(String[] args) {
        ThisDemo tt=new ThisDemo();
         tt.increment().increment().increment().print();
    }
}

一个类中定义两个构造函数,在一个构造函数中通过 this 这个引用来调用另一个构造函数

public class ThisDemo {  
    String name;
    int age;
    public ThisDemo (){ 
        this.age=21;
   }     
    public ThisDemo(String name){
        this();
        this.name="Mick";
    }     
  private void print(){
         System.out.println("最终名字="+this.name);
         System.out.println("最终的年龄="+this.age);
    }
    public static void main(String[] args) {
       ThisDemo tt=new ThisDemo("zhangsan"); //随便传进去的参数
       tt.print();
    }
}

练习

创建Dog类

编写Test类

QzEVvmE.png!mobile

package com.company;

/**
 * Created by ttc on 2017/12/28.
 */
//private ,default, protected,public
public class Dog {
    private String name = "旺财"; // 昵称
    private int health = 100;     // 健康值0---100 private私有的
    private int love = 0;        // 亲密度
    private int type;//类型:1狗2企鹅
    private int kind;//品种

    public String toString()
    {
        String strKind = "";
        if(kind == 1)
        {
            strKind = "拉布拉多";
        }
        else if(kind == 2)
        {
            strKind = "雪纳瑞";
        }
        String str = "宠物的自白,我的名字叫"
                +name+"健康值是"+health+"和主人的亲密度是"+love+"我是一只"+strKind;
        return str;
    }

    public String getName() {
        return name;
    }

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

    public int getHealth() {
        return health;
    }

    public void setHealth(int health) {
        this.health = health;
    }

    public int getLove() {
        return love;
    }

    public void setLove(int love) {
        this.love = love;
    }

    public int getType() {
        return type;
    }

    public void setType(int type) {
        this.type = type;
    }

    public int getKind() {
        return kind;
    }

    public void setKind(int kind) {
        this.kind = kind;
    }
}
package com.company;

import java.util.Scanner;

public class Main {

    public static void main(String[] args) {

        Scanner scanner = new Scanner(System.in);
        System.out.println("欢迎来到宠物店");
        System.out.println("请输入宠物名字");

        String name = scanner.next();

        System.out.println("请输入宠物类型:1狗,2企鹅");
        int type = scanner.nextInt();
        if(type == 1)
        {
            Dog d = new Dog();
            System.out.println("请输入品种,1聪明的拉布拉多,2酷酷的雪纳瑞");
            int kind = scanner.nextInt();
            d.setKind(kind);
            d.setName(name);
            System.out.println(d);
        }
        else
        {
            //new 企鹅();
        }

    }
}

创建Penguin类

编写Test类

zem63ev.png!mobile


Recommend

About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK