Java学习-面向对象基础

目录

1.设计对象

2.内存机制

3.面向对象实战:购物车案例

4.构造器、this

4.1构造器

4.2 this

5.封装

6.JavaBean

7.成员变量和局部变量

8.案例


1.设计对象

什么是面向对象呢,顾名思义,首先你要先有个对象,然后要面向对象,然后才能解决问题(

那么既然你没有对象,如何设计对象呢?

首先对象是什么呢:

对象就是你的女朋友(不是),对象可以是一台电脑,一辆汽车,一个人,你的女朋友(一本正经),而这些对象都有属性,比如大小、颜色、年龄等等,同样可以定义行为,如移动。

那如何设计对象呢:

首先要定义一个类,然后在类里面定义属性。说了这么多,不如演示一下。下面我定义一个人类。

package com.zwcode.object;

public class Test01 {
    public static void main(String[] args) {
        //这样我的女朋友(一个人 类)就定义出来了
        People myGirlFriend = new People();
        myGirlFriend.name = "小仙女";
        myGirlFriend.age = 18;//永远18岁
        myGirlFriend.run();
    }

}

//类名-我的女朋友
class People{
    //姓名
    String name;
    //年龄
    int age;

    //可以定义行为如跑步
    public void run(){
        System.out.println(name + "在跑步");
    }
}

定义完人这个类后就可以new出一个对象,这里就是我的女朋友,我可以定义她的姓名年龄等等,运行结果如下:

小仙女在跑步

同样的,定义完一个人类后,不仅能new出我的女朋友,还可以new出别的人,比如第二个女朋友(不是),比如你的父母老师等等都可以,只要是人就可以。

下面再new出一个人并给出一些定义

//再定义一个人
        People myTeacher = new People();
        myTeacher.name = "张麻子";
        myTeacher.age = 46;
        myTeacher.run();

运行结果

小仙女在跑步
张麻子在跑步

在定义类时,需要注意的几点:

2.内存机制

值得注意的是:局部变量存在栈中,其中s1也是局部变量也叫引用;new出来的对象存在堆内存中,它的地址赋给在栈中的引用部分。

3.面向对象实战:购物车案例

需求:模拟购物车模块的功能,需要实现添加商品到购物车中去,同时需要提供修改商品的购买数量,结算商品价格功能。

分析:购物车中每个商品都是一个对象,需要定义一个商品类;购物车本身也是一个对象,可以使用数组代表它;完成界面结构,让用户选择操作的功能。

  • 添加商品:add
  • 查看商品:query
  • 修改数量:update
  • 结算价格:pay

请您选择要操作的功能:

代码如下:

package com.itzw.practice;

import java.util.Scanner;

public class ShopCarTest {
    public static void main(String[] args) {
        //创建一个购物车,可以存放100个商品
        Goods[] shopCar = new Goods[100];


        while (true){
            //菜单
            System.out.println("添加商品到购物车:add");
            System.out.println("查看购物车的商品:query");
            System.out.println("修改购物车商品数量:update");
            System.out.println("结算购物车商品价格:pay");
            System.out.println("请您选择要操作的功能:");
            //开始选择功能
            Scanner sc = new Scanner(System.in);
            String commend = sc.next();

            switch (commend) {
                case "add":
                    //添加商品
                    addShop(shopCar, sc);
                    break;
                case "query":
                    //查看商品
                    queryShop(shopCar);
                    break;
                case "update":
                    //修改数量
                    updateShop(shopCar, sc);
                    break;
                case "pay":
                    //结算价格
                    payShop(shopCar);
                    break;
                default:
                    System.out.println("输入错误,请重新输入!");
                    break;
            }
        }

    }

    public static void payShop(Goods[] shopCar) {
        //总价格
        double sum = 0;
        for (int i = 0; i < shopCar.length; i++) {
            if (shopCar[i] != null){
                sum += shopCar[i].price * shopCar[i].buyNumber;
            }else{
                break;
            }
        }
        System.out.println("购物车商品总价格为:" + sum);
    }

    public static void updateShop(Goods[] shopCar, Scanner sc) {
        while (true){
            System.out.println("请输入要修改的商品的编号:");
            int id = sc.nextInt();
            Goods g = getGoodsById(shopCar,id);
            if (g == null){
                System.out.println("找不到该商品!");
            }else{
                System.out.println("请输入需要修改该商品的数量:");
                int updateNumber = sc.nextInt();
                g.buyNumber = updateNumber;
                queryShop(shopCar);
                break;
            }
        }
    }

    //根据编号得到商品对象
    public static Goods getGoodsById(Goods[] shopCar, int id){
        for (int i = 0; i < shopCar.length; i++) {
            if (shopCar[i] == null)
                return null;
            else{
                if (shopCar[i].id == id)
                    return shopCar[i];
            }
        }
        return null;
    }

    public static void queryShop(Goods[] shopCar) {
        System.out.println("购物车商品如下:");
        System.out.println("=======================");
        System.out.println("编号\t\t\t名称\t\t\t价格\t\t\t数量");
        for (int i = 0; i < shopCar.length; i++) {
            //要先判断对象是否为空
            if (shopCar[i] == null)
                break;
            else
                System.out.println(shopCar[i].id+"\t\t\t"+shopCar[i].name+"\t\t\t"
                        +shopCar[i].price+"\t\t\t"+shopCar[i].buyNumber);
        }
    }

    public static void addShop(Goods[] shopCar, Scanner sc) {
        //输入编号
        System.out.println("请输入编号:");
        int id = sc.nextInt();
        //输入名称
        System.out.println("请输入名称:");
        String name = sc.next();
        //输入价格
        System.out.println("请输入价格:");
        double price = sc.nextDouble();
        //输入购买数量
        System.out.println("请输入数量:");
        int buyNumber = sc.nextInt();

        //创建一个商品对象
        Goods g = new Goods();
        g.id = id;
        g.name = name;
        g.price = price;
        g.buyNumber = buyNumber;

        //把新创建的对象存入购物车
        //存入前要判断购物车下标,是否已经被使用
        for (int i = 0; i < shopCar.length; i++) {
            if (shopCar[i] == null) {
                shopCar[i] = g;
                break;
            }
        }
        System.out.println("添加成功!");
    }
}


class Goods {
    int id;//编号
    String name;//名称
    double price;//价格
    int buyNumber;//购买数量
}

本次案例知识模拟购物车,很多东西都没有考虑,日后再完善。

4.构造器、this

4.1构造器

构造器的作用:用于初始化一个类的对象,并返回对象的地址

构造器格式:如下展示了构造器的格式,分为有参和无参

  • 无参构造:初始化对象时成员变量采用默认值。
  • 有参构造:在初始化对象时,同时可以接受参数对变量赋值。
class Student{
    String name;
    int age;

    //无参构造
    public Student(){
        System.out.println("无参构造执行了。。。");
    }

    //有参构造
    public Student(String n, int a){
        System.out.println("有参构造执行了。。。");
        name = n;
        age = a;
    }
}

下面演示一下无参构造和有参构造的区别,在main方法中输入以下代码

public static void main(String[] args) {
        //创建s1对象用无参构造
        Student s1 = new Student();
        System.out.println(s1.name + "   " + s1.age);
        //创建s2对象用有参构造
        Student s2 = new Student("张麻子",45);
        System.out.println(s2.name + "   " + s2.age);
    }

运行结果:

无参构造执行了。。。
null   0
有参构造执行了。。。
张麻子   45

从结果可以发现,和前面说到的结论一样。

值得注意的是:

  • 任何类定义出来,默认就自带了无参构造器,写不写都有
  • 一旦定义了有参构造器,name无参构造器就没有了,如果还想用无参构造器,此时就需要自己手写一个无参构造器了。
  • 建议大家在创建好类时,之间就无脑写上有参和无参构造器,写上总是没错的。

4.2 this

this是什么:this代表了当前对象的地址。这个知识点很关键!

下面用代码演示一下

public class Test01 {
    public static void main(String[] args) {
        Car car = new Car();
        car.run();
        System.out.println(car);
    }
}
public class Car {
    public Car(){
        System.out.println("午餐构造的this" + this);
    }

    public void run(){
        System.out.println("方法中的this" + this);
    }
}

运行得到的结果:我们发现三处的this结果是一样的,都是当前对象的地址。

午餐构造的thiscom.itzw.thisdemo.Car@1b6d3586
方法中的thiscom.itzw.thisdemo.Car@1b6d3586
com.itzw.thisdemo.Car@1b6d3586

this的作用:用于指定访问当前对象的成员变量、成员方法。

怎么理解这个作用呢,在上面我们写到有参构造时,参数名最好是能和成员变量名一样,这样更方便理解,但是又不能写一样的,这样编译器就不好理解了,它分辨不出此时的变量名是参数还是当前对象的变量,给有参构造赋值就会失败。这时this就派上了用处,因为this是用于访问当前对象的,话不多说,下面演示一下。

package com.itzw.thisdemo;

public class Test02 {
    public static void main(String[] args) {
        Student s1 = new Student("马邦德",45);
        System.out.println(s1.name + "   " + s1.age);
        
        s1.friend("张麻子");
    }
}

class Student{
    String name;
    int age;

    public Student() {
    }

    //有参构造
    public Student(String name, int age) {
        this.name = name;
        this.age = age;
    }

    public void friend(String name){
        System.out.println(this.name + "是" + name + "的朋友");
    }

}

运行结果:

马邦德   45
马邦德是张麻子的朋友

如果去掉this,结果必然是错误的,可自行演示一下

5.封装

什么是封装:

  • 告诉我们,如何正确设计对象的属性和方法。
  • 原则:对象代表什么,就得封装对应的数据,并提供数据对应的行为。

好处:

  • 让编程变得简单,有什么事,找对象,掉方法就行。
  • 降低学习成本,不用记对象的那么多方法有需要时去找就行。
  • 建议每次定义好类的成员变量时就立刻封装。

下面演示一下封装:

package com.itzw.fengzhuang;

public class Test01 {
    public static void main(String[] args) {
        Person p1 = new Person();
        p1.setAge(100);
        System.out.println(p1.getAge());
    }
}


class Person{
    private int age;

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        if (age >= 0 && age <= 150){
            this.age = age;
        }else{
            System.out.println("您输入的年龄有误");
        }
    }
}

这样我们就不能随意修改年龄,只能通过set方法修改,并且可以在set方法里面做限制,本次限制年龄在0-150之间,若超过这部分则提示出错,会输出默认值0。

6.JavaBean

JavaBean也称为实体类,其对象可用于在程序中封装数据

标准JavaBean需满足如下书写要求:

  • 成员变量使用private修饰。
  • 提供成员变量对应的set和get方法。
  • 必须提供一个无参构造器;有参构造器可以不写。

代码演示:

package com.itzw.javabean;

public class Test01 {
    public static void main(String[] args) {
        
    }
}

class User{
    private String name;//姓名
    private double heigth;//身高
    private double salary;//薪水

    public User() {
    }

    public User(String name, double heigth, double salary) {
        this.name = name;
        this.heigth = heigth;
        this.salary = salary;
    }

    public String getName() {
        return name;
    }

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

    public double getHeigth() {
        return heigth;
    }

    public void setHeigth(double heigth) {
        this.heigth = heigth;
    }

    public double getSalary() {
        return salary;
    }

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

以上就是标准JavaBean,我们发现,这其实就是前面学到的构造器和封装的结合,我们在写类时,建议写成这种形式。

下面使用一下标准JavaBean:

public class Test01 {
    public static void main(String[] args) {
        //使用无参构造
        User user1 = new User();
        user1.setName("张麻子");
        user1.setHeigth(180);
        user1.setSalary(1000);
        System.out.println(user1.getName());
        System.out.println(user1.getHeigth());
        System.out.println(user1.getSalary());

        //使用有参构造
        User user2 = new User("马邦德",179,10000);
        System.out.println(user2.getName());
        System.out.println(user2.getHeigth());
        System.out.println(user2.getSalary());
    }
}

7.成员变量和局部变量

成员变量:

  • 在类中,方法外
  • 有默认值,无需初始化
  • 在堆内存中
  • 随着对象的创建而存在,随着对象的消失而消失
  • 作用域无法确定,在类外创建对象就可以访问,在类内也可以访问

局部变量:

  • 常见于方法中
  • 没有默认值,使用之前要赋值
  • 在栈内存中
  • 随着方法的调用而存在在,随着方法的运行结束而消失
  • 作用域为在所属的大括号中

8.案例

模仿电影信息展示

package com.itzw.demo;

public class MovieTest {
    public static void main(String[] args) {
        //创建三个电影对象,封装信息
        Movie m1 = new Movie("长津湖",9.8,"吴京");
        Movie m2 = new Movie("斗牛",8.8,"黄渤");

        //定义一个电影数组,存放三部电影
        Movie movies[] = new Movie[3];
        movies[0] = m1;
        movies[1] = m2;
        //也可以直接在后面new一个对象,不需要先new再存入,这样更方便
        movies[2] = new Movie("无人区",9.9,"徐峥");
        
        //输出电影信息
        for (int i = 0; i < movies.length; i++) {
            System.out.println("名称:" + movies[i].getName());
            System.out.println("评分:" + movies[i].getScore());
            System.out.println("主演:" + movies[i].getActor());
            System.out.println("================================");
        }
    }
}

class Movie{
    private String name;
    private double score;
    private String actor;

    public Movie() {
    }

    public Movie(String name, double score, String actor) {
        this.name = name;
        this.score = score;
        this.actor = actor;
    }

    public String getName() {
        return name;
    }

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

    public double getScore() {
        return score;
    }

    public void setScore(double score) {
        this.score = score;
    }

    public String getActor() {
        return actor;
    }

    public void setActor(String actor) {
        this.actor = actor;
    }
}

输出结果:

名称:长津湖
评分:9.8
主演:吴京
================================
名称:斗牛
评分:8.8
主演:黄渤
================================
名称:无人区
评分:9.9
主演:徐峥
================================

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值