What's the Difference Between Struct Based and Class Based Singletons

What's the difference between Struct based and Class based singletons?

The main difference is that class-based mutable singleton works, while struct-based mutable "singleton" doesn't. Unless you want to make your singleton immutable (which is rare) you should stick to the class-based one.

Here is an illustration of how mutable struct-based "singleton" does not work. Consider adding a mutable member state to both singletons, like this:

class MyClassSingleton {
static let sharedInstance = MyClassSingleton()
private init(){}
var state = 5
func helloClass() { print("hello from class Singleton: \(state)") }
}

struct MyStructSingleton {
static let sharedInstance = MyStructSingleton()
private init() {}
var state = 5
func helloStruct() { print("hello from struct Singleton: \(state)") }
}

I made state a var, but I could expose it as a read-only property plus a mutating method; the essential thing is that both types are now mutable.

If I do this

let csi = MyClassSingleton.sharedInstance
csi.state = 42
MyClassSingleton.sharedInstance.helloClass()

42 gets printed, because csi is referencing the shared instance.

However, when I do the same thing with struct-based singleton

var ssi = MyStructSingleton.sharedInstance
ssi.state = 42
MyStructSingleton.sharedInstance.helloStruct()

5 gets printed instead, because ssi is a copy of the sharedInstance, which is, of course, an indication that our singleton is not actually a singleton.

Why we should use struct and class function in singleton pattern?

Actually it is recommended to use your second code because of the improvements in the versions of swift.One more thing that you should consider is to declare your singleton object using static let and also make the initializer private

class Bar{

private init(){
// initialization
}

static let shared = Bar()

}

Use self in singleton struct

A couple of thoughts:

  1. A struct singleton is a contradiction in terms. A singleton is an object where there should be only one instance. But struct is a value-type and has "copy" memory semantics. Consider:

    var a = StructA.shared
    ...

    The a is a copy of the so-called singleton, not a reference to it. To avoid this problem, the singleton should be a class, a reference type.

  2. I agree with Paulw11, that self is a simpler and more common approach. I'd also suggest, though, that by referencing self, you can better write code that (a) is not dependent on the class being a singleton; and (b) opens the possibility of the class being subclassed at some future date.

  3. Given that I would advise self pattern, I would therefore also suggest avoiding obvious potential strong reference cycles (e.g. by employing weak or unowned references where needed). There's no point in knowingly creating what could be strong reference cycle simply because it happens to be a singleton. Why write code that you know you'd have to rewrite if you ever revisited the decision to use singleton pattern, especially when you know how easy it is to avoid strong references in the first place?

  4. FYI, I'm seeing the same behavior that you report, that if a static participates in a theoretical strong reference cycle, it's not identified as such. But if you set that static property to nil (assuming it was variable and optional), the strong reference appears.

    This observation doesn't change my recommendation above, namely to avoid what you know would be a strong reference cycle in any other context. I'm merely confirming your empirical observation.

Regarding points 2 through 4 above (where I contemplate some potential eventual refactoring of singleton pattern into some other pattern), I should say that this is not a purely academic observation. It's not uncommon to have some singleton type, and later, as the project becomes more complicated or employs more unit tests, to revisit that decision and start employing dependency injection or other patterns. It would be a shame if you had to edit all of the individual functions as well. If you write the code to not depend upon the singleton nature of the object, you end up with more robust code base with fewer unnecessary internal dependencies.

What's the difference between these two singleton class structures?

In c#, Private Constructor is a special instance constructor and it is used in a classes that contains only static members. If a class contains one or more private constructors and no public constructors, then the other classes are not allowed to create an instance for that particular class except nested classes.

constructor is private, Because we don't want any outer class create an instance of this class.

and about performance, in version 1 you have to check: if instance of class is empty then create an instance, But in version 2 you have a static constructor with a readonly field, that mean the instance will be initialized when class call for the first time and for the next call static constructor never called again.

For more explanation about singleton pattern, you can follow this link

Patterns: Singletons vs. Static vars and methods approach

A class-based singleton is the way to go, provided you accommodate for dependency injection for your tests. The way to do this is to create a single singleton for your app, called, say, DependencyManager. In your AppDelegate (or from other classes if needed), you'd create whatever controllers, network services, realm models, etc you want to hang on your DependencyManager, and then assign them to the DependencyManager. This code would be skipped by your unit tests.

Your unit tests can then access the DependencyManager (and thus instantiate the DependencyManager during first access), and populate it with mock versions of those controllers and services to whatever degree each unit test desires.

Your UIViewControllers, your MVVM view models, etc... can access the DependencyManager as a singleton, and thus get either the real controllers and services, or a mock version of them, depending on if you're running the app or unit tests.

If you're doing MVVM, I also recommend that when a UIViewController is about to create its view model class, that it first checks a special property in the DependencyManager to see if a mockViewModel exists. A single property can serve this purpose, as only one of your UIViewControllers ever would be tested at once. It'd use that property instead of creating a new view model for itself. In this way, you can mock your view models when testing each UIViewController. (There's other tricks involved to being able to prop up a single UIViewController for testing, but I won't cover that here).

Note that all of the above can work very nicely with an app that also wants to use storyboards and/or nibs. People are so down on storyboards because they can't figure out how to do dependency injection of mock services for their view controllers. Well, the above is the solution! Just make sure in your AppDelegate to load the storyboard AFTER setting up the DependencyManager. (Remove the storyboard name from your info.plist, and instantiate it yourself in AppDelegate).

I've written a few shipped apps this way, as well as some sample apps for an SDK, along with the tests. I highly recommend the approach! And be sure to write your unit tests and viewController tests either during or at least immediately after development of each such class, or you'll never get around to them!

What is the difference between a Class and a Singleton in Objective-C?

You are programming in Objective-C, an Object-oriented programming language (OOP). So, to know what a class is, you must first understand OOP concepts.

I wont go into why OOP languages was developed as opposed to procedural languages. You can google "procedural vs objective oriented advantages".

Anyway,
Object Oriented Programming languages (OOP) provide mechanisms/devices/structures that helps you implement OOP principles. 3 main principles are (1)Encapsulation (2)Inheritance (3) Polymorphism. Again google to find out what these are.

Now a Class: would be one of those mechanisms/devices/structures that implements the 3 OOP principles. It is a blueprint/design/structure of what an object should be.
Typically (but not always) a class would have (1) variables declared within it (strings, int, arrays, whatever) and (2) Methods/functions that perform a task on those declared variables within it. When you instantiate/allocate/create-that-class-in-memory, that class becomes "alive". The blueprints now become an object (an object that implements the OOP principles you are supposed to google).

Now a Singleton is a design pattern. If you're a coming from a procedural language environment, there are many programming design patterns you may need to catch up on. A Singleton is a pattern/a-particular-way-you-design-someting. So when you say a singleton class, it is a particular way you design that class. And what is that particular design? Well, usually when you instantiate/allocate/create-a-class-in-memory, you can do it many times, there by creating multiple instanced objects of that class. If you apply a singleton design pattern to a class however, you ensure that only one instance (and ONLY one) can be created.

In Objective-C if i do something like this:

myClass *anObjectOfMyClass1 = [[myClass alloc] init];
// This (above) would create an object from the blueprint *myClass* and assign it to *anObjectOfMyClass1*
myClass *anObjectOfMyClass2 = [[myClass alloc] init];
// This would create an object from the blueprint *myClass* and assign it to *anObjectOfMyClass2*
// Note: anObjectOfMyClass1 and anObjectOfMyClass2 would contain two different objects of the same type
// If *myClass* was designed using singleton pattern however, anObjectOfMyClass1 and anObjectOfMyClass2 would typically contain the same object.

In short.. you really cant compare the two.
As for the usage of singletons.. I would say Loggers. I think there are already answers around stackoverflow about uses of singletons. Look around a bit.

Difference between static function and singleton class in swift

Sure this sounds confusing and can be debated. However, from the best practices i can put some suggestions.

Singleton is usually used to create a resource intensive and one timer initialisation for instance: a database connector, login handler and such.

Utility class are classes that only have static functions and variables. It should not deal with async task and expensive resource handling like opening a database connector.

In your case, if the utility is doing some resource intensive process its better to wrap in a singleton. If not, then Static functions in a class is better in my opinion. This is so also because, Swift will dispatch all static functions in a class using static dispatch. Whereas this cannot be true in Singleton although Swift likes to optimizes.

Static Dispatch are 4 times faster than Dynamic Dispatch as far as Objective-C runtime is used. This is true for swift too. However, it only takes 4 nano seconds to dispatch Dynamiclly.

I hope this makes you clear.

How do you choose between a singleton and an unnamed class?

I think the most important reason is that you cannot put an unnamed class in namespace scope. So, the following is not valid (gcc accepts, but warns. comeau doesn't accept in strict mode):

class { } single;
int main() { }

The type of single has no linkage because there is no way to declare its name in another scope referring to it (precisely because it has no name). But using it to declare single, which has linkage (external here) is not valid (3.5/8). single has to be defined locally in main where it will have no linkage. You also cannot pass single to function templates and it can't have static data members (because there is no way to define them). All those restrictions make it more or less not applicable as a substitution for a singleton.



Related Topics



Leave a reply



Submit