سؤال

I have an Orders class and i need to have a singleton pattern to be able to create a sequence number for each order processed. How do i implement this?

My order class has an Order_ID, Customer_ID, Order_desc and Ordered_qty. There needs to be a sequence number created for each order processed using the singleton pattern.

هل كانت مفيدة؟

المحلول

This may be one of those X/Y problems, where you think Y is a solution to X, so you ask for help with Y, but perhaps there is a better solution.

Strictly speaking, to implement a singleton, all you need is a class whose only constructors are private, a static reference to an instance of the class as a class field, and a public getInstance method. Then create an instance method which returns the next number in line.

public class MySingleton {
    private static MySingleton instance = new MySingleton();

    private volatile int next = 0;

    private MySingleton() {
        // prevent external instantiation of a singleton.
    }

    public static MySingleton getInstance() {
        return instance;
    }

    public synchronized int getNextSequence() {
        return next++;
    }
}

There are many flaws with this solution to your problem, some are just basic OOP design and some are more systemic:

  1. A singleton that does not implement or extend any types is worthless. You could just use all static methods instead. Singletons are useful if you are writing a class that implements an interface and that interface is used by somebody else, but you only want a single instance as an implementation detail. This type of singleton is an attempt to make a global variable look like it is not a global variable.
  2. This will not survive application restarts. If these sequences are being used to identify data that is stored externally or shared, you will end up repeating the same numbers when the application is restarted.
  3. If you deploy multiple instances of the application who read and write to a common persistent storage, like a database, they will re-use the same numbers because the sequence is only tracked within the JVM.
  4. Databases are already exceptionally good at this. Trying to re-invent it in the application tier seems.... inappropriate.

نصائح أخرى

Although I agree @Elliott Frisch that the question itself sounds strange. However if you indeed have to generate IDs yourself here is the prototype that implements classic version of Singleton pattern.

public class IdGenerator {
    private  static IdGenerator instance;
    private int id = 0;
    private IdGenerator(){}
    private static IdGenerator getInstance() {
        synchronized(IdGenerator.class) {
           if (instance == null) {
                instance = new IdGenerator();
           }
           return instance;
        }
    }

    public int nextId() {
        return id++;
    }
}

Please note that word "classic". There are a lot of possible improvements of Singleton pattern and there are hundreds of articles that explain them.

The key aspect is to use a single AtomicLong as the singleton. You may model it like this:

class Orders {

    private static final AtomicLong NEXT_ID = new AtomicLong();

    static Order newOrder(Customer customer, String description, int quantity) {
        return new Order(orderId(), customer, description, quantity);
    }

    private static long orderId() {
        return NEXT_ID.incrementAndGet();
    }
}

class Order {

    private final long orderId;
    private final long customerId;
    private final String description;
    private final int quantity;

    Order(long orderId, Customer customer, String description, int quantity) {
        this.orderId = orderId;
        this.quantity = quantity;
        this.customerId = customer.getCustomerId();
        this.description = description;
    }

}

class Customer {

    public long getCustomerId() {
        throw new UnsupportedOperationException("not yet implemented");
    }
}
مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top