华清远见重庆中心—面向对象技术总结/个人总结

目录

方法

调用方法

1.通过类名调用

Math类

 2.通过对象调用

3.在同一个类中,方法A直接调用方法B

 方法调用总结

 自定义方法

方法的类型

无参数无返回值

无参数有返回值

有参数有返回值

注意

编程思想

面向过程编程

面向对象编程

总结

类和对象

类Class

属性

行为

定义类

对象Object

创建对象

类和对象的关系

成员变量和局部变量

成员变量

局部变量

构造方法

概念

特点

IDEA中自动生成构造方法

面向对象语言的三大特性--封装

封装

步骤

IDEA中自动生成getter/setter方法

IDEA中自动使用变量接收对象

Windows中的快捷键

Typora中的快捷键

IDEA中常用快捷键

面向对象三大特性--继承

概念

特点

方法重写和方法重载

方法重写override

方法重写要求

方法重载overload

方法重载要求

this和super关键字

当做对象使用

当做构造方法使用

注意

包package

包的命名

导入包

访问修饰符

访问权限表

final关键字

修饰方法

修饰类

创建对象时的内存变化

 Object类

对象造型/对象转型/cast

向下转型

向上转型

重写equals方法

在IDEA中自动生成equals方法

Manager类

Shop类

面向对象三大特性--多态

多态的应用

多态的前提

多态应用案例--“花木兰替父从军”

Woman类

 Soldier类

 BattleGround类

Main

abstract抽象的

修饰方法

修饰类

abstract关键字特点

修饰类:被修饰的类称为抽象类

修饰方法:被修饰的方法称为抽象方法

接口interface 

extends和implements

类A extends 类B

类A implements 接口A,接口B...

接口A extends 接口B

类A extends 类B implements 接口A,接口B...

什么时候使用接口

定义接口

接口案例

USB接口

USB接口的实现类--鼠标类和键盘类

使用接口的类--电脑类

Main

抽象类和接口的异同

static静态的

在不使用静态成员时

使用静态成员时

 概念

定义和访问

什么时候使用static

static特点

成员变量、局部变量、静态常量

成员变量:定义在类中的变量

局部变量:定义在方法中的变量

静态常量:被final、static修饰的成员变量

可变参数

枚举

定义枚举类型

使用枚举类型

内部类

匿名内部类

使用案例

USB接口

创建一个USB的实现类--鼠标类

Lambda表达式

Lambda表达式语法

使用lambda表达式遍历集合

Work

模拟"电子宠物"

Pet

 PetMachine

Test

Main

模拟组装手机

Hardware

Camera

CPU

Screen

Main

模拟游戏厅

GameHouse

Game

GameDemo

GameNum

Player

Main

Hero

HeroManager

Main

面试题

成员变量和局部变量相关面试题

简述成员变量和局部变量的区别以及生命周期

重载和重写相关面试题

说出重载与重写的异同

构造方法能重载吗?能重写吗?

构造方法在执行时,一定会创建对象吗?

以下代码执行会输出什么结果

抽象相关面试题

抽象类的特点?

抽象类中有构造方法吗?

执行某个类的构造方法时,一定会创建这个类的对象吗?

面向对象的特点?

你怎么理解面向对象?

面向对象和面向过程的区别?

接口和抽象类的区别是什么 ?

成员变量与局部变量的区别有那些 ?

创建一个对象用什么运算符?对象实体与对象引用有何不同?

什么是方法的返回值?返回值在类的方法里的作用是什么?

一个类的构造方法的作用是什么?若一个类没有声明构造方法,该程序能正确执行吗 ?为什么?

构造方法有哪些特性 ?

对象的相等与指向他们的引用相等,两者有什么不同?

在调用子类构造方法之前会先调用父类没有参数的构造方法,其目的是?

构造块、静态块、构造方法中的方法执行顺序是怎样的?

普通类和抽象类有哪些区别?

 抽象类能使用 final 修饰吗?

补充:关于 final 关键字的一些总结

基础总结


方法

方法是定义在类中的一段独立代码,能完成某个事情

定义方法时,提供方法的名称、返回值类型、参数列表,这三点成为方法的三要素,定义的方法都需要这三部分

当在使用该方法中的代码时,只需通过该方法名调用即可

方法能够减少代码冗余

调用方法

1.通过类名调用

Math类

Math类是Java中的工具类,用于数学计算

该类中的方法和属性都使用static修饰,可以直接通过类名调用

在任何类中,通过快捷键ALT + 7,展示方法列表

 

System.out.println(Math.PI);//圆周率
System.out.println(Math.E);//自然常数
System.out.println(Math.abs(-5));//绝对值
System.out.println(Math.max(1,2));//最大值
System.out.println(Math.min(2.5,3.2));//最小值
System.out.println(Math.ceil(2.1));//向上取整
System.out.println(Math.floor(3.9));//向下取整
System.out.println(Math.round(-1.5));//四舍五入
System.out.println(Math.random());//[0,1)之间的随机数
System.out.println(Math.sqrt(9));//平方根
System.out.println(Math.cbrt(27));//开立方
System.out.println(Math.pow(2,3));//2的3次幂

 2.通过对象调用

创建对象:类名 对象名 = new 类名([参数])

Scanner sc = new Scanner(System.in);
sc.方法名;

Random rd = new Random();
rd.方法名;

3.在同一个类中,方法A直接调用方法B

class Test{
      void funA(){
          funB();
      }
      void funB(){
          System.out.println("我是B方法");
      }
}

 方法调用总结

调用方式:

通过类名调用

通过对象调用

直接调用

参数:

无参数

Scanner sc = new Scanner(System.in);
sc.next();//调用无参数方法

 有参数

Random rd = new Random();
rd.nextInt(10);

 返回值

没用返回值,方法名的前面用void表示

class Test {
    void funB(){
        System.out.println("我是B方法");
    }
    public static void main(String[] args) {
        Test t = new Test();
        t.funB();
    }
}

 有返回值

Random rd = new Random();
rd.nextInt(10);

 自定义方法

方法的三要素:

1.方法名:

使用驼峰命名法

2。方法返回值类型:

如果有返回值,使用Java中的任意数据类型,方法体中使用return关键字返回对应类型的数据

如果没有返回值,使用void关键字 

3.方法参数列表:

参数写法:数据类型 形参名,数据类型 形参名 

[修饰符] 返回值类型 方法名(参数列表){
    方法体;
}

方法的类型

无参数无返回值

void 方法名(){
     //方法体
     return;//遇到return立即结束方法
}

无参数有返回值

void 方法名(数据类型 形参名,数据类型 形参名){
     //方法体
     return;
}

有参数有返回值

//生成a,b中包含最小值,不包含最大值范围内的随机数
double rand(int a,int b){
    double num = Math.floor(Math.random()*Math.abs(a-b)+Math.min(a,b));
    return num;
}

注意

有返回值的方法,必须要在方法体中加入return并能够执行,同时要return一个该方法返回值类型 对应的数据。

没有返回值的方法,可以不用加入return关键字。如果加入return关键字,不能跟上数据。

方法中出现return,会立即结束方法。所以return语句之后不能再有代码。

定义方法时的参数称为形式参数,简称形参;调用方法时,实际传递的参数称为实际参数,简称实 参。实参只需保证数据类型和形参相同即可。

编程思想

面向过程编程

Procedure Oriented Programming 简称POP。

是一种基本的编程思想,将一件事情按流程按步骤执行,逻辑清晰。

每一步都是基于上一步的流程去继续实现。

注重于分析问题的步骤。

如果逻辑复杂,如xxx管理系统,使用POP就会变得很麻烦。

C语言就是一门面向过程的编程语言。

面向对象编程

Object Oriented Programming 简称OOP。

是一种编程思想,核心是创建解决问题的对象,赋予对象行为和特征,让这些对象互相配合执行。

每个对象的行为实际也是面向过程的。

注重于全局如何创建完成某件事情的对象,如果适时地调用。

这种思想致力于将计算机中的世界,描述的和现实中一致的思想。

总结

面向过程:亲力亲为,侧重于分析完成事情的过程

面向对象:所有事情交给相应的对象完成,侧重于如何创建解决问题的对象

类和对象

类Class

具有相同属性和行为的对象的集合。相当于模板。

属性

描述这个类的特征值,在程序中,通过定义变量实现。

行为

描述这个类的动作,在程序中,通过定义方法实现。

创建一个class文件,就是创建一个类。

定义类

[修饰符] class 类名{

          //属性(定义变量)

          //行为(定义方法)

}

/*
* 定义车的模板
* 属性:变量
* 品牌
* 颜色
* 座位数
* 排量
*
* 行为:方法
* 跑
* 说话
* 飞
*
* */
public class Car {
    //定义变量 数据类型 变量名 ;
    String brand;
    String color;
    int seat;
    //定义方法
    void run(){
        System.out.println("车在跑。。。");
    }
    void introduce(){
        //在方法中可以直接访问同一个类中的属性
        System.out.println("我是一辆"+brand+"牌的"+color+"色的"+seat+"座车");
    }
}

对象Object

对象由某个类创建出来的具体实例。

创建对象

类名 对象名 = new 构造方法([参数]);

创建出的对象,通过"."操作符访问类中的非私有属性和方法。

public class Test4 {
    public static void main(String[] args) {
        // 创建Car类的对象
        //类名 对象名 = new 类名();
        Car benz = new Car();
        //对象.类中的属性和方法
        benz.seat = 5;
        benz.color="白";
        benz.brand="奔驰";

        benz.introduce();
        benz.run();
    }
}

类和对象的关系

对象是类的具体表现,类是对象的模板。

如制作月饼的模具就是一个类,每次用这个模具创建出来的月饼就是一个对象。

先定义类,才能通过该类获取对象。

成员变量和局部变量

成员变量

定义在类中的变量,称为成员变量,有默认值。

整数类型 默认值
整型 0
浮点型 0.0
布尔型 false
引用类型(类、数组、接口) null
class Person{
    String name;//成员变量,String是类类型,属于引用类型,默认为null
    int age;//整型,默认0
    double[] list;

    void fun(){
        System.out.println(name);//这里能通过编译,可以使用name,输出null
        System.out.println(list[0]);//这里能通过编译,由于list为null,会报空指针异常
    }
}

局部变量

定义在方法中的变量,称为局部变量。没有默认值,赋值后才能使用。

class Test{
    public static void main(String[] args){
        int num;//定义在方法中的变量称为局部变量,赋值后才能使用
        System.out.println(num);//无法通过编译
    }
}

构造方法

概念

构造方法也称为构造函数、构造器、constructor

它是一个特殊的方法。

没有返回值部分,方法名和类名一致,在创建对象时通过new调用,给类的成员变量赋值。

class Person{
    //成员变量
    String name;
    int age;

    //这就是一个无参数的构造方法,用于new Person()
    Person(){

    }
    //这就是一个带参数的构造方法,用于new Person("admin",20)
    Person(String name,int age){
        this.name=name;//将参数的值赋值给成员变量
        this.age=age;
    }
}

特点

  • 创建对象时必须通过new配合构造方法
  • 构造方法没有返回值部分,名称和类名相同
  • 构造方法可以存在多个,但是参数不能相同。这些构造方法之间的关系称为方法重载
  • 每个类默认有一个隐藏的无参数的构造方法,方法体中隐含了一句super()。用于创建无参数的对象
  • 如果自己写了带参数的构造方法,默认无参数的构造方法就会失效。如果想要同时拥有带参数和不 带参数的构造方法, 就需要再次显式地写出来
  • 带参数的构造方法常用于初始化成员变量(给类中的变量赋值)
  • 构造方法可以限制创建对象时携带的参数
  • 构造方法无法通过"."操作符访问,只能通过new关键字创建对象时调用

IDEA中自动生成构造方法

在类空白处右键generate或快捷键alt+insert

面向对象语言的三大特性--封装

封装

使用private关键字对成员变量进行修饰。再提供一组get和set的方法,用于对该属性读取和赋值。

可以防止除自身类之外的地方对private修饰的属性进行访问。

这样就能保护关键属性或给属性赋一个合理的值。

步骤

1.创建类,编写成员变量,对成员变量使用private修饰

class Person{
    private String name;
    private int age;
}

2.给所有成员变量添加set方法,用于赋值

void setName(String name){
    this.name=name;
}
    void setAge(int age){
    this.age=age;
}

3.给所有成员变量添加get方法,用于读取

String getName(){
    return name;
}
    int getAge(){
    return age;
}

创建该类对象后,无法直接通过.访问属性,只能通过get/set读取和赋值

public static void main(String[] args){
    Person p = new Person();
    //p.name;//无法通过.访问被private修饰的属性
    p.setName("王海");
    String name = p.getName();
}

IDEA中自动生成getter/setter方法

在类中空白处右键generate或快捷键alt + insert,在弹出的窗口中选择getter and setter

IDEA中自动使用变量接收对象

在对象后.var或快捷键ctrl+alt+v

public static void main(String[] args) {
    //创建对象自动使用变量保存 ctrl + alt + v 或 对象.var
    Employee employee = new Employee();
}

Windows中的快捷键

windows + D    进入桌面

windows + E    进入文件资源管理器

Typora中的快捷键

1-6级标题    CTRL + 1~6

加粗    选中文字 CTRL + B

倾斜    选中文字 CTRL + l

倾斜    选中文字 CTRL + U

列表    - 空格 缩进 tab

表格    CTRL + T

整段代码    ```语言

嵌入代码    代码

IDEA中常用快捷键

复制粘贴    CTRL + D

自动接收对象    CTRL + ALT + V

自动生成构造方法等    ALT + Insert

自动调整格式    CTRL + ALT + L

删除整行    CTRL + X

CTRL + Y    可以设置为删除整行或配合撤销(CTRL + Z)恢复

面向对象三大特性--继承

概念

类B使用extends(延伸)关键字"继承"类A。

语法:class 类B extends 类A{}

类B称为类A的子类,衍生类,subClass

类A称为类B的父类,超类、supClass

继承后,子类就能访问父类中的非私有(没有使用private修饰)成员变量和成员方法。

class A{
    private String secret="父类中的私有属性";
    String name="父类";
    void info(){
        System.out.println("父类中的非私有方法");
    }
}
class B extends A{
    void fun(){
        System.out.println(secret);//无法访问父类中的私有成员变量
        System.out.println(name);//可以访问非私有成员变量
        info();//可以直接调用父类中的非私有方法
    }
}

将多个类中的公共代码提取出来保存到一个公共类中,这些类使用extends"继承"这一个公共类,从而减 少这些类中的冗余代码。

如猫类、狗类都有类型、昵称等属性,也有吃、睡等方法,那就可以定义一个动物类,将这些公共的属 性和方法定义在动物类这个父类中,

再让猫类和狗类这些子类继承动物类。这样就能直接通过子类访问父类中的内容。

特点

  • 如果多个类之中有相同的代码,可以将这些代码提取出来到一个公共的类中,这个类就是父类。再 让那些类去extends继承这个父类,那些类就是子类。子类就无需再写重复代码
  • 子类中或子类对象可以直接访问父类中非私有(不用private修饰)属性和方法
  • 创建子类对象时,会先执行父类中相应的构造方法
  • 子类继承父类后,通常会对对父类中的方法进行拓展或覆盖,这称为方法重写。重写后,子类再调 用该方法时,执行的是重写后的内容
  • Java中是单继承。一个子类只能extends一个父类,一个父类可以有很多子类
  • Java中可以多重继承,类A可以继承类B,类B继承类C,这是类A既是类B的子类,也是类C的子 类,类A可以访问类B和类C中的非私有成员
  • 任何类都是Object类的子类

方法重写和方法重载

方法重写override

当子类继承父类后,可以对父类中的方法进行扩展或覆盖。这个过程称为方法重写。

方法重写要求

  • 方法名、返回值、参数列表必须和父类一致
  • 访问权限不能比父类更严格(访问修饰符的范围要么一致要么更大)
  • 不能抛出比父类更大的异常

IDEA中如果要重写方法,使用CTRL + O在弹出的窗口中选择要重写的方法

方法重载overload

在一个类中,如果多个方法的方法名相同,参数列表不同时,这些方法称为重载的方法。

同名不同参。

重载用于,在一个类中,某个方法在不同的条件下,执行不同的内容。

方法重载要求

  • 方法名相同
  • 参数必须不同(数量、类型)
  • 与返回值无关

this和super关键字

这两个关键字,都可以当做对象使用,也可当做构造方法使用。

当做对象使用

用法:this.属性或this.方法,super.属性或super.方法

此时的this表示当前类的对象,super表示当前类的父类对象

class Person{
    private String name;
    public void setName(String name){
        //这里的this表示当前类的对象Person对象
        //相当于Person p = new Person();中的p
        this.name=name;
    }
    public String getName(){
        return name;
    }
}

class Man extends Person{
    void fun(){
        //这里的super表示当前类的父类对象
        //Person p = new Person();
        //super表示上句话中的p
        System.out.println(super.getName());
    }
}

当做构造方法使用

用法:this([参数])或super([参数]) 此时的this([参数])表示当前类的某个构造方法。如this()表示当前类的无参构造方法。

super([参数])表示当前类的父类的某个方法。如super()表示当前类的父类的无参构造方法。

如果当做构造方法使用时,只能写在另一个构造方法的第一行。

class Person{
    String name;
    int age;
    Person(){
}
    Person(String name,int age){
        this.name=name;
        this.age=age;
    }
}

class Woman extends Person{
    Woman(){
        super("admin",20);
    }
}
class Main{
    public static void main(String[] args){
        //调用Woman中的无参构造方法
        //super("admin",20),执行父类中的 Person(String name,int age)
        new Woman();
   }
}

注意

如果父类中有无参数的构造方法,在子类的构造方法中,可以不写super(),默认自动调用。

如果父类中有带参数的构造方法,没有无参数的构造方法,在子类的构造方法中,必须要有super([参 数])。

父类和子类中都没有构造方法(只有默认的无参构造方法)

class Father{
    //默认会有
    /*
        public Father(){}
    */
}
class Son extends Father{
    //默认会有
    /*
        public Son(){
            super();
       }
    */
}

父类中没有无参构造方法,子类中就必须调用父类中对应的构造方法

class Father{
    String name;
    //由于该构造方法的出现,默认无参数的构造方法就会失效
    Father(String name){
        this.name=name;
    }
}

    //这时子类继承会报错
class Son extends Father{
    //因为每个类中都有这段代码
    /*
    Son(){
        //但当前继承的父类中没有无参构造方法
        super();
    }
    */
}

//解决方式1.给父类中添加无参构造方法
class Father{
    String name;
    Father(String name){
        this.name=name;
    }
    Father(){
    }
}

//解决方式2.子类中添加同样的构造方法,目的是为了调用父类中的对应构造方法
class Son extends Father{
    Son(String name){
        super(name);
    }
}

包package

通过包可以将.java源文件进行结构化管理,相当于windows中的文件夹。

不同的包中,可以保存相同的.java源文件。

某个类在某个包中时,会在该类的代码最上加入 package 包名 ;

包的命名

包名通常使用公司域名的倒序形式。

如baidu.com是百度的域名,有一个test的项目,包名写为com.baidu.test

包名中的".",相当于进入文件夹

如com.baidu.test,会创建3个文件夹:com下有baidu,baidu下有test。

导入包

如a包中的类要使用b包中的类时,需要在a包中的类中,导入b包或b包中的某个类。

如在使用Scanner时,就需要导入Scanner所在的java.util包。 import java.util.Scanner;

在IDEA中,如果是通过自动补全的形式写的代码,会自动导入该类,

或设置自动导包删包。

如果需要手动导入包,在报错的位置上按下快捷键alt+回车,

如果多个类,类名相同但在不同的包中,使用该类时选择合适的包。

访问修饰符

访问修饰符可以限制某个类、属性或方法的访问权限

用法:

修饰类:访问修饰符 class 类名{}

修饰属性:访问修饰符 数据类型 变量名;

修饰方法:访问修饰符 返回值类型 方法名(){}

 

访问修饰符 含义 可以修饰
public 公共的 类、方法、属性
protected 受保护的 方法、属性
不写 默认的 类、属性、方法
private 私有的 方法、属性

访问权限表

同一个类中 同一个包中的不同类 不同包中的子类 不同包中的非子类
public
protected ×
不写 × ×
private × × ×

访问权限从大到小

public >>> protected >>> 默认的 >>> private

final关键字

当final修饰属性时,该属性的值不可更改,这个属性称为常量。

常量在程序运行过程中,保存的值不能编号,所以定义常量时需要初始化。

常量名所有字母大写,多个单词之间用_隔开。

final 数据类型 常量名;
final int NUM = 123;
final double PI = 3.14;

修饰方法

当final修饰方法时,该方法不能被重写。

在方法的返回值前加上final。

public class Father{
    public final void fun(){
    }
}
public class Son extends Father{
    //会报错,无法对final方法进行重写
    @Override
    public void fun(){
    }
}

修饰类

当final修饰类时,该类不能被继承。

定义类,在class前加final

public final class Father{
    public final void fun(){
    }
}
//会报错,提示该类无法继承Father
public class Son extends Father{
}

创建对象时的内存变化

 Object类

是java中所有类的父类。每个类都是这个类的子类,但没有使用extends体现出来

该类中定义了很多方法,通常需要进行重写。

常用方法 返回值 作用
toString() String 在输出某个对象时,会默认调用该方法。该方法默认输出"包名. 类名@十六进制哈希码"。通常用于重写后输出对象的属性。
equals(Object obj) boolean 判断两个对象是否相同。Object类中默认使用==比较,通常需要 重写该方法,自定义比较的规则。
hashcode() int 得到对象的哈希码。哈希码可以理解为对象的内存地址,经过一 个特定的算法得到的一个特定值。
getClass() Class 得到某个对象所在的类。
notify() void 唤醒某个线程
notifyAll() void 唤醒所有线程
wait(long time) void 让线程休眠,直到被唤醒
finallize() void 当某个对象被垃圾回收机制GC回收前执行的方法

对象造型/对象转型/cast

类似于原始类型中的数据类型转换。对象A转换为对象B的过程,称为对象转型。

在非继承关系的两个对象中,无法转型。

向下转型

父类对象转换为子类对象的过程,称为向下转型。强制转换

//一个父类对象
Object obj = new Object();
//默认无法直接将obj使用Person对象接收
//"强制转换"
Person p = (Person) obj;

向上转型

子类对象转换为父类对象的过程,称为向上转型。自动转换

//一个子类对象
Person p = new Person();
//默认子类对象可以用父类变量接收 多态
Object obj = p;

重写equals方法

如果两个对象的属性全部相同,在日常的业务逻辑中,可以视为这两个对象是同一个对象。

但是默认使用new创建的对象,就算属性一致,也是不同的内存地址,

如果用==比较,比较的是对象的内存地址,地址不同,返回false。

所以对象比较相同不能使用==

这时就需要自定义一套比较的方法,Object中有一个equals方法,用于比较两个对象是否相同,

但是Object中的equals方法用==比较,所以对该方法进行重写。

如两个Student的id、name、sex都一致,返回true.

@Override
public boolean equals(Object obj) {
    //将Object对象转换为当前类Student对象
    if (this == obj) {
        return true;
    }
    //判断参数是否为Student类型
    //对象 instanceof 类 检测对象是否属于指定类型
    if (obj instanceof Student) {
        //使用"强制转换"将父类对象转换为子类对象,称为向下转型
        Student student = (Student) obj;
        if (this.id == student.id &&
            this.name.equals(student.name) &&
            this.sex.equals(student.sex)) {
            return true;
        }
    }
    return false;
}

在IDEA中自动生成equals方法

在类中右键generate或快捷键alt + insert,选择equals and hashcode,选择属性。

如两个对象的id相同就视为同一个对象,可以只选择id属性;

如两个对象的所有属性相同才视为同一个对象,选择全部属性。

同时生成的hashcode()可以删除。

Manager类

package com.hqyj.test3;
import java.util.Objects;
/*
* 登录系统的管理员类
* 属性
* 账号
* 密码
* 方法
* 全参构造
* 无参构造
* getter/setter
* toString
* equals
* */
public class Manager {
    private String username;
    private String password;

    @Override
    public String toString() {
        return "Manager{" +
            "username='" + username + '\'' +
            ", password='" + password + '\'' +
            '}';
    }

    @Override
    public boolean equals(Object o) {
        //判断是否是同一个对象
        if (this == o) return true;
        //是否为空,是否属于同一种类
        if (o == null || getClass() != o.getClass()) return false;
        //向下转型
        Manager manager = (Manager) o;
        //遍历所有属性判断是否一致
        //Objects是一个工具类,equals()方法判断两个参数是否相同,实际使用参数的equlas方法判
断
        return Objects.equals(username, manager.username) &&
Objects.equals(password, manager.password);
    }

    public Manager() {
    }

    public Manager(String username, String password) {
    this.username = username;
    this.password = password;
    }

    public String getUserna
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值