在 Java 中,创建一个类实例最简单的方法就是使用 new
关键字,通过构造函数来实现对象的创建。
People people = new People();
实际开发中,还有另一种创建类实例的方法,通过静态工厂方法在类中添加一个公有静态方法来返回一个实例
class People {
String name;
int age;
int weight;
public static People getPeople(){
return new People();
}
}
然后通过getPeople这个静态方法来获取一个实例:
People people = People.getPeople();
静态工厂方法的特点:
- 优势
1.静态工厂方法有名称
Java构造函数必须与类名相同,重载只能通过参数类型/数量区分。当多个构造器参数类型相同时,开发者可通过调整参数顺序实现重载,单参构造器无法实现。而用静态工厂方法代替构造器,用不同的方法名实现不同初始化逻辑,从而创建不同属性的对象,可以解决此问题。
举个例子
假设有一个 Person 类,需要根据相同参数类型(比如 String)初始化不同属性(如 name 或 id),但构造器无法区分这两种情况:public class Person { private String name; private String id; // ❌ 无法通过参数类型区分两个构造器(都是String) public Person(String name) { this.name = name; } public Person(String id) { this.id = id; } // 编译报错:重复构造器 }
静态工厂方法的解决方式:
public class Person { private String name; private String id; // 私有构造器,限制外部直接new private Person() {} // ✅ 静态工厂方法:通过方法名区分逻辑 public static Person createWithName(String name) { Person p = new Person(); p.name = name; return p; } public static Person createWithId(String id) { Person p = new Person(); p.id = id; return p; } }
使用示例:
Person person1 = Person.createWithName("张三"); // 初始化name属性 Person person2 = Person.createWithId("ID-123"); // 初始化id属性
2.静态工厂方法不用在每次调用的时候都创建一个新的对象
举个例子
假设我们有一个 Color 类,表示 RGB 颜色。通过静态工厂方法 fromRGB 创建颜色对象时,复用已存在的相同颜色对象,而不是每次都新建:public class Color { private final int r, g, b; private static final Map
CACHE = new HashMap<>(); // 缓存池 // 私有构造器,禁止外部直接 new private Color(int r, int g, int b) { this.r = r; this.g = g; this.b = b; } // ✅ 静态工厂方法:复用已有对象 public static Color fromRGB(int r, int g, int b) { String key = r + "," + g + "," + b; // 检查缓存中是否存在相同颜色 Color cachedColor = CACHE.get(key); if (cachedColor == null) { cachedColor = new Color(r, g, b); CACHE.put(key, cachedColor); // 存入缓存 } return cachedColor; } } 使用示例:
Color red1 = Color.fromRGB(255, 0, 0); Color red2 = Color.fromRGB(255, 0, 0); System.out.println(red1 == red2); // 输出 true ✅ 两个引用指向同一个对象
第一次调用 fromRGB(255,0,0):创建新对象,存入缓存。
第二次调用 fromRGB(255,0,0):直接返回缓存中的对象,不再新建。对比构造器的行为:
如果直接通过构造器 new Color(255,0,0),每次都会创建新对象:Color red3 = new Color(255, 0, 0); // ❌ 假设构造器是公开的 Color red4 = new Color(255, 0, 0); System.out.println(red3 == red4); // 输出 false ❌ 两个不同对象
- 实际应用场景: