I'm a physicist working on a scientific code. Apologies if this is a routine question: it may well have been answered before, but I don't have the software engineering background to quite tell.
Basically, the code needs to perform a large number of matrix multiplications by a small number of different matrices. Constructing the matrices in the first place is very expensive, so I'd like them to persist between uses. However, the class which does the multiplication has no way of knowing what the matrices willl be during its initialization. They will vary substantially over its lifetime, and the same matrix will generally be used by multiple instances of the multiplication class.
It seems to me that the Singleton pattern applies in this situation: we can create a pool of matrices, keyed by whatever distinguishes them from one another. Then, the multiplication classes can access that pool whenever it needs a matrix.
Here's a sketch of what I have in mind:
//SingletonDictionary.hpp class SingletonDictionary : private NonCopyable { public: void Clear(); //Calls member variable destructors. ~SingletonDictionary() { Clear(); } private: friend SingletonDictionary& TheSingletonDictionary(); SingletonDictionary() {}; //Only the friend can make an instance. //Retrieve searches through the key vectors for a match to its //input. In none is found, the input is added to the key vectors, //and a new Value is constructed and added to the ValueVector. //In either case the ValueVector is returned. std::vector<double>& Retrieve(const int key1, const int key2); std::vector<int> mKey1; std::vector<int> mKey2; std::vector<double> mValue; } //SingletonDictionary.cpp SingletonDictionary& TheSingletonDictionary() { static SingletonDictionary TheSingleton; return TheSingleton; } //DoMatrixMultiply.cpp void ApplyTransformation(std::vector<double> data){ const int key1 = data.size()[0]; const int key2 = data.size()[1]; SingletonDictionary TheSingletonDictionary(); std::vector<double> TransformMatrix = TheSingletonDictionary.Retrieve(key1, key2); DGEMM("N", "N", data.Data(), TransformMatrix.Data(),.....); } NonCopyable is an abstract base class that disables the copy constructor, etc.
I'm wondering if this is an appropriate circumstance for this pattern. If not, what else might work?