演示非延迟初始化线程安全的Java程序
Java是 Oracle 提供的最流行的面向对象编程语言之一,它在开发人员探索的网站和应用程序开发中具有广泛的应用。 Java与一些知名且健壮的框架(如 Spring、Spring-Boot 等)一起使开发人员在开发/编码软件时的生活变得轻松。 Java提供了 2 种对象实例化(Object Instance Creation)方式,即 Eager 和 Lazy。本文重点介绍非延迟实例化(即 Eager Instantiation)。
Java中的线程是小的独立编码单元,可以单独执行(在 CPU 的多个核心上并行执行)以提高处理速度等。因此, Java的线程安全意味着无论创建多少线程并同时执行输出或业务程序执行的逻辑保持如预期或期望的那样。对于像单例这样的简单示例(在执行代码期间只应存在 1 个实例,并且除了创建第一个实例外,允许实例化此类的新/不同实例)在Java的类
因此,本文试图阐明线程安全环境中的非延迟实例化,并通过汽车制造商(制造商)案例研究示例的实际说明来帮助解释它。
执行:
以下将是通过CarMaker来演示解释对象的非延迟实例化的方法。 Java (下面的脚本)为例。
- 我们有一个Car Java类(它充当单例类),因此在整个程序流程中只需创建和提供一个对象。
- 我们有一个CarMaker类(其中包含main() 方法的Runner 类),它尝试获取基本 Car 实例并使用它执行设计、绘制和增强等操作(在我们的确切情况下,这些是带有适当的简单打印语句消息)
- 我们为上述所有操作创建了单独的线程以演示线程安全行为(在我们的例子中,这意味着即使并发线程到达getCarIntance()方法,也只有一个实例会在程序中循环)
- 线程执行的顺序可能会改变,但使用非延迟实例创建创建单个对象(将在终端上打印相同的对象 ID 时可见)的结果将在这里得到满足。
例子
Java
// Java Program to illustrate Implementation of non
// Lazy-Instantiation (Eager Instantiation)
// which is Thread-Safe
// Importing required libraries
import java.io.*;
import java.util.*;
import java.util.concurrent.*;
// 'CarMaker' class is trying to Manufacture a Car
// So the Base vehicle 'Car' should remain same and
// operations like paintCar,designCar,enhanceCar etc.
// will execute with the same Car (Object Instance here.)
// Class 1
// Helper class
// Refers to a Singleton Class in General
class Car {
// Creating eager instance variable for Car
// Thread-Safe as marked final
private static final Car car = new Car();
// Only executes when new Car Instance is created
// So Ideally this should be executed only once as
// we are working with same Car
// Constructor of Car class
private Car()
{
// Print and display message
// should be displayed only once on terminal.
System.out.println("New Car is Created");
}
// Method of Car class
static Car getCarInstance()
{
// Returns the Car Instance
return car;
}
}
// Class 2
// Main class
class CarMaker {
// Main driver method
public static void main(String args[])
{
// We make threads dynamically for
// each operation specified above
// Thread 1
// Thread for designing the Car
Thread designCar = new Thread(new Runnable() {
// run() method for thread
public void run()
{
// Creating and getting the Car instance
Car car = Car.getCarInstance();
// Print and display the ID
System.out.println(
"Designing Car with id : " + car);
}
});
// Thread 2
// Thread for Painting the Car
Thread paintCar = new Thread(new Runnable() {
// run() method for thread
public void run()
{
// Creating and getting Car instance by
// calling the Car class method
Car car = Car.getCarInstance();
// Print and display the ID
System.out.println("Painting Car with id : "
+ car);
}
});
// Thread 3
// Thread for Enhancing the Car
Thread enhanceCar = new Thread(new Runnable() {
// run() method for the thread
public void run()
{
// Creating and getting Car instance by
// calling the Car class method
Car car = Car.getCarInstance();
// Print and display the ID
System.out.println("Enhancing Car with id : "
+ car);
}
});
// Note: Second object of Car class can not be
// created Cannot create new Instance as Constructor
// is not Visible
// Below object is not created
// in first compile and run
// It is cleared here in second go
// during compile and run
// Car car2 = new Car();
// Running the above 3 threads as created above
designCar.start();
paintCar.start();
enhanceCar.start();
}
}
输出:
这里我们编译了程序两次,其中第二次我们强行创建了第二个“Car”类对象。请注意,我们无法创建“Car”类的第二个实例,因为第二次构造函数不可见。它会抛出一个错误,如下面下划线部分的图片硬编码输出所示,当我们编译并通过创建另一个对象再次运行时,它会抛出到终端上。
输出说明:
在这里,为了解释Java类对象的非延迟实例化,我们进行了一个简单的案例研究,即拥有制造汽车的汽车标记。它使用基本的“汽车”车辆并执行诸如油漆汽车、设计汽车和增强汽车之类的操作。为了尽可能简单地处理,我们在每个操作中都有简单的打印语句以及汽车对象 ID 的显示,以确保它们在同一辆车上工作。
正如我们在输出中看到的,操作(在本例中为线程)的执行顺序可能不同,但 Car Object Id 在程序执行过程中保持不变,以说明在其上执行的每个操作(绘制、设计和增强)同一辆车。正如在单例 (Car) 实例创建时的代码注释“ final”关键字中所解释的那样,它对于执行来说是线程安全的,因此我们得到了始终具有相同 Car 对象的期望结果。
Conclusion: Do refer in order to figure out how “final” make the code thread-safe without having synchronization. Thus, the above article explains non-Lazy Instantiation (Eager Instantiation) of Java classes (Singleton classes) with the help of Car Maker case study example.