JavaSE基础——第六章 类与对象(二)

四、作用域

在 Java 中,变量根据其作用域和生命周期可以分为 局部变量全局变量(通常指成员变量)。

1. 局部变量(Local Variables)

定义

  • 声明位置 :在方法、构造方法、代码块(如 {})内部声明。
  • 作用域:仅限于声明它的方法或代码块内部。
  • 生命周期:从声明处开始,到方法/代码块执行结束时销毁。
  • 初始化必须显式初始化,否则编译报错。
java 复制代码
public class Example {
    public void demoMethod() {
        int localVar = 10; // 局部变量
        System.out.println(localVar);
    }

    public static void main(String[] args) {
        Example obj =0 new Example();
        obj.demoMethod();
        // System.out.println(localVar); // 错误!localVar 在此不可见
    }
}
  • 线程安全:每个线程调用方法时会创建独立的局部变量副本。
  • 无默认值 :必须手动赋值(如 int x = 0;)。
  • 属性和局部变量可以重名,访问时遵循就近原则
  • 在同一个作用域中,例如同一个成员方法中,两个局部变量不能重名

2. 全局变量(成员变量,Member Variables)

定义

  • 声明位置:在类内部、方法外部声明。
  • 作用域:整个类内部(所有方法均可访问)。
  • 生命周期:与对象共存亡(实例变量)或与类共存亡(静态变量)。
  • 初始化自动赋予默认值 (如 int 默认为 0,对象默认为 null)。

分类

  1. 实例变量(Instance Variables)
    • 属于对象,每个对象有独立副本。
    • 通过 对象.变量名 访问。
  2. 静态变量(Static Variables)
    • 属于类,所有对象共享同一副本。
    • 通过 类名.变量名 访问。
java 复制代码
public class Example {
    // 实例变量(全局变量)
    int instanceVar = 20;

    // 静态变量(全局变量)
    static String staticVar = "Hello";

    public void printVars() {
        System.out.println(instanceVar); // 访问实例变量
        System.out.println(staticVar);  // 访问静态变量
    }

    public static void main(String[] args) {
        Example obj1 = new Example();
        obj1.instanceVar = 30; // 修改 obj1 的实例变量
        Example.staticVar = "World"; // 修改静态变量(影响所有对象)

        Example obj2 = new Example();
        System.out.println(obj2.instanceVar); // 输出 20(默认值)
        System.out.println(obj2.staticVar);  // 输出 "World"(静态变量共享)
    }
}
  • 默认值 :无需显式初始化(如 int 默认为 0)。
  • 线程风险:实例变量和静态变量可能被多线程共享,需同步控制。

3. 关键对比

特性 局部变量 全局变量(成员变量)
声明位置 方法/代码块内部 类内部,方法外部
作用域 仅限于声明块内 整个类
生命周期 方法/代码块执行期间 对象存活期(实例变量)或程序运行期(静态变量)
初始化 必须显式初始化 自动赋予默认值
线程安全 是(每个线程独立副本) 实例变量:否;静态变量:需同步
访问方式 直接使用变量名 实例变量:对象.变量名;静态变量:类名.变量名
存储位置 栈内存 堆内存(实例变量)/方法区(静态变量)

五、构造方法/构造函数/构造器

类的一种特殊方法,主要用于完成对新对象的初始化(属性的值)。构造器被调用时对象已经存在,仅完成属性初始化。

java 复制代码
[修饰符] 方法名(形参列表) {
		方法体;
}

类名 对象名 = new 类名(实参列表);
  • 一个类可以定义多个不同的构造器,即构造器的重载(例如分别初始化不同的属性)
  • 修饰符可以是任意一个
  • 构造器没有返回值
  • 方法名和类名必须一样
  • 在创建新对象时,系统自动调用构造器对对象进行初始化,不能主动调用
  • 如果没有定义构造方法,系统会自动给类生成一个默认无参构造方法,例如Person(){}。可以通过javap命令反编译.class文件提供的字节码获得源码(输出的构造函数是一个声明)。
  • 一旦定义构造器,默认的构造器就被覆盖,不能再使用默认的无参构造器;除非显示定义无参构造器

⭐对象创建流程:

六、this关键字

输出结果为null 0,因为在构造器中相当于局部变量自己给自己赋值,对对象属性的值没有影响。

  • JVM会给每个对象分配this,代表当前对象

  • 可以认为对象中有个隐藏的属性this,是一个引用,指向该对象所在的地址

  • 简单地将hashCode()方法认为获取对象的地址,会根据不同的对象返回不同的整数,是将该对象的内部地址转换成一个整数实现的。因为Java代码在JVM上运行,不能直接获取地址

  • this可以访问本类的属性、方法、构造器

  • 可以用于区分当前类的属性和局部变量

  • 访问成员方法:this.方法名(参数列表);

  • 访问构造器:this(参数列表);只能在构造器中使用该语句访问另一个构造器,并且该语句必须放在第一条,不能使用多条

  • 不能再类定义的外部使用,只能在类定义的方法中使用

🐈‍⬛生成随机整数

例如在 Java 中,生成 0~6 之间的随机整数 (包括 0 和 6),可以使用 java.util.RandomMath.random()。以下是两种方法的实现:

方法 1:使用 java.util.Random

java 复制代码
import java.util.Random;

public class RandomExample {
    public static void main(String[] args) {
        Random random = new Random();
        int num = random.nextInt(7); // 生成 [0, 6] 的随机整数
        System.out.println("随机数: " + num);
    }
}

关键点

  • random.nextInt(7):生成范围 [0, 6] 的整数(参数 7 是上限,不包含 7)。
  • 需要导入 java.util.Random

方法 2:使用 Math.random()

java 复制代码
public class RandomExample {
    public static void main(String[] args) {
        int num = (int) (Math.random() * 7); // 生成 [0, 6] 的随机整数
        System.out.println("随机数: " + num);
    }
}

关键点

  • Math.random():返回 [0.0, 1.0)double 值。
  • 7:将范围扩展到 [0.0, 7.0)
  • (int):强制转换为整数,截断小数部分,得到 [0, 6]

扩展:生成指定范围的随机数

如果需要生成 [min, max] 范围内的随机整数(如 1~6):

java 复制代码
// 使用 Random
int num = random.nextInt(max - min + 1) + min; // 例如 random.nextInt(6) + 1 → [1, 6]

// 使用 Math.random
int num = (int) (Math.random() * (max - min + 1)) + min; // 例如 (int)(Math.random() * 6) + 1 → [1, 6]

注意事项:

  1. 范围边界Random.nextInt(n) 的范围是 [0, n-1],而 Math.random() * n 的范围是 [0, n)
  2. 线程安全Random 是线程安全的,但多线程环境下更推荐用 ThreadLocalRandom(Java 7+)。
  3. 种子控制Random 可以指定种子(如 new Random(123)),用于生成可重复的随机序列。
相关推荐
矛取矛求1 小时前
C++ 标准库参考手册深度解析
java·开发语言·c++
cijiancao1 小时前
23 种设计模式中的解释器模式
java·设计模式·解释器模式
南七行者1 小时前
对模板方法模式的理解
java·设计模式·模板方法
٩( 'ω' )و2601 小时前
stl_list的模拟实现
开发语言·c++·list
麻芝汤圆1 小时前
MapReduce 的广泛应用:从数据处理到智能决策
java·开发语言·前端·hadoop·后端·servlet·mapreduce
努力的搬砖人.1 小时前
java如何实现一个秒杀系统(原理)
java·经验分享·后端·面试
珊瑚里的鱼1 小时前
第五讲(下)| string类的模拟实现
开发语言·c++·笔记·程序人生·算法·visualstudio·visual studio
哈哈哈哈哈哈哈哈哈...........2 小时前
【java】在 Java 中,获取一个类的`Class`对象有多种方式
java·开发语言·python
@小白向前冲2 小时前
python 重要易忘 语言基础
开发语言·python
fallwind_of_july2 小时前
java项目分享-分布式电商项目附软件链接
java·redis·分布式·mongodb·elasticsearch·微服务·rabbitmq