简单实现单例,避免样板代码

如果需要使用双重校验锁实现单例,可以考虑使用GuavaSuppliers.memoize(),避免手写样板代码。

package current;

import java.util.Random;

import com.google.common.base.Supplier;
import com.google.common.base.Suppliers;

/**
 * Created on 2022-09-29
 */
public class SingletonTest {

    private static final Supplier<SingletonTest> heavySupplier =
            Suppliers.memoize(SingletonTest::new);

    private SingletonTest() {
        System.out.println("being created" + new Random().nextInt(9));
    }

    public static SingletonTest getSingleton() {
        return heavySupplier.get();
    }

    public static void main(String[] args) {
        for (int i = 0; i < 5; i++) {
            SingletonTest heavyObject = SingletonTest.getSingleton();
            System.out.println(heavyObject);
        }
    }
}

结果

being created2
current.SingletonTest@3d24753a
current.SingletonTest@3d24753a
current.SingletonTest@3d24753a
current.SingletonTest@3d24753a
current.SingletonTest@3d24753a

Process finished with exit code 0

Suppliers.memoize方法

/**
   * Returns a supplier which caches the instance retrieved during the first
   * call to {@code get()} and returns that value on subsequent calls to
   * {@code get()}. See:
   * <a href="http://en.wikipedia.org/wiki/Memoization">memoization</a>
   *
   * <p>The returned supplier is thread-safe. The supplier's serialized form
   * does not contain the cached value, which will be recalculated when {@code
   * get()} is called on the reserialized instance.
   *
   * <p>If {@code delegate} is an instance created by an earlier call to {@code
   * memoize}, it is returned directly.
   */
  public static <T> Supplier<T> memoize(Supplier<T> delegate) {
    return (delegate instanceof MemoizingSupplier)
        ? delegate
        : new MemoizingSupplier<T>(Preconditions.checkNotNull(delegate));
  }

  @VisibleForTesting
  static class MemoizingSupplier<T> implements Supplier<T>, Serializable {
    final Supplier<T> delegate;
    transient volatile boolean initialized;
    // "value" does not need to be volatile; visibility piggy-backs
    // on volatile read of "initialized".
    transient T value;

    MemoizingSupplier(Supplier<T> delegate) {
      this.delegate = delegate;
    }

    @Override public T get() {
      // A 2-field variant of Double Checked Locking.
      if (!initialized) {
        synchronized (this) {
          if (!initialized) {
            T t = delegate.get();
            value = t;
            initialized = true;
            return t;
          }
        }
      }
      return value;
    }

    @Override public String toString() {
      return "Suppliers.memoize(" + delegate + ")";
    }

    private static final long serialVersionUID = 0;
  }

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值