Difference between lazySingleton and singleton in Get_it - flutter

Currently, I am using get_it package for dependency injection. However, I have confused about singleton and lazySingleton.
I know its difference is lazySingleton will not init until it's used and reduce init time as well as saving resource. However, I don't know what is drawbacks of lazySinglton with singleton are. Why not replace all singleton with lazySingleton.

Both are Singletons. But LazySingleton refers to a class whose resource will not be initialised until it's used for the 1st time. It's generally used to save resources and memory.
Now the drawback, LazySingleton will take time when it is used for the first time. the other singleton may have been initialized in advance and the time taken to initialize might have been used to make the process faster.

Related

Play framework compile-time dependency injection and singleton

I have been refactoring my Play app from using Guice to using Compile-time DI.
In Guice, when we don't decorate a class with #Singleton, many instances can be created as needed.
In compile-time DI, we create an instance to be injected once, thus I think it is equivalent to a singleton.
My question is if I would lose any performance by restricting everything to be only one instance. For example, if I have an instance serviceA, with method doSomething, and considering that everything is stateless. If I have a 32-core CPU, and lots of requests come in. Would Play, in the context of compile-time DI, be able to utilize the full capacity of the CPU?
AFAiK Guice (and other runtime DI frameworks) doesn't by default produce singletons for the sole reason to be faster when creating the instances and simplify complex (potentially cyclic) dependency graph. Their goal is to start faster.
Whether you have 1 or 2 instances of ServiceA will not affect the performance of using these instances once they are created.
It's theorically even better to have singletons.

Storing app wide instance. Static field vs pass instance as argument

Say I have an instance of a class which i need access to in many different places of my app. I have come up with three solutions so far
Passing the instance as an argument in every class of the app
Making a top level Provider above the MaterialApp-widget that exposes the instance to every method that has access to the app's context
Storing the instance in a static field
Which way is the best performance wise? Will the Flutter-framework ever discard the instance stored in the static field?
Which way is the best performance wise? Will the Flutter-framework ever discard the instance stored in the static field?
In this case, I like to use the DI framework like get_it
With the DI you can specify what is the object that you want and you can have it in your Wiget or Component, without coupled it with the specific implementation.
Use the get started guide to see how it is simple to use and what are the benefits.
Get Started
Suggestion
I suggest wrapping the library in one component inside your app, with the only motivation that with your own wrapper around the DI library you avoid to coupled all the app with the get_it, and you can change it easily in the future if you want.
Not sure about the performance, but the second option (Provider way) is what I am using in my projects and that's even a recommended approach (https://flutter.dev/docs/development/data-and-backend/state-mgmt/options#provider).
Passing the instance as an argument in every class of the app
This could lead to a very cumbersome code, every constructor would be cluttered by the same property passing all the way down to the Widget tree - not a Flutter way at all, that's why InheritedWidget was introduced some time ago, and later - Provider.
Storing the instance in a static field
It depends. E.g. it is ok to store all the colour constants inside a class having static fields - that's just convenient to access them everywhere. This option could also work in your case (not sure about the size and the amount of information stored in that class instance), but implementing your class as a Singleton would probably make more sense than storing the whole instance in a static field.

how to get all instances of a given class/trait with scala reflect? all refs to a given instance?

I know it's possible to get the members of a class, and of a given instance, but why is it hard to get all instances of a given class? Doesn't the JVM keep track of the instances of a class? This doesn't work in Java:
myInstance.getClass.getInstances()
Is this possible with the new scala reflect library? Are there possible workarounds?
Searched through the reflection scaladoc, on SO and google, but strangely couldn't find any info on this very obvious question.
I want to experiment/hack a hypergraph-database, inspired by hypergraphDB, querying the object graph directly, set aside serialization.
Furthermore, I'd need access to all references to a given object. Now this information certainly is there (GC), but is it accessible by reflection?
thanks
EDIT: this appears to be possible at least by "debugging" the JVM from another JVM, using com.sun.jdi.ReferenceType.instances
"Keeping track" of all instances of a class is hardly desirable, at least not by default. There's considerable cost to doing so and the mechanism must avoid hard references that would prevent reclaiming otherwise unreferenced instances. That means using one of the reference types and all the associated machinery involved.
Garbage Collection does not need to be class-aware. It only cares about whether instances are reachable or not.
That said, you can write code to track instantiations on a class-by-class basis. You'd have to use one of the reference classes in java.lang.ref to track them.

Consequences of Singletons

So I just delved into the Singleton classes and yes, I find them quite helpful. I use my singletons mostly for data storage for multiple targets (views, tables etc.). That being said, I can already see myself going to implement a lot of singletons in my project.
But can a lot of singletons have a negative impact? From what I've read about singletons is that you create one instance for each of them in a proces. Other class instances get released (assuming they get released properly) from memory, then should singletons be released too?
So to narrow it down to one question: Is it harmful to have a lot of singletons?
Singletons don't scale. No matter what you think should be a singleton, when your system gets bigger, it turns out you needed more than one.
If you NEVER need more than one, a singleton is fine. However, as systems scale, you typically need more than one of anything within its own context.
Singletons are merely another way to say "global". It's not bad, but generally, it's not a good idea for systems that evolve and grow in complexity.
From GOF Book:
The Singleton pattern has several benefits:
Controlled access to sole instance. Because the Singleton class encapsulates its sole instance, it can have strict control over how
and when clients access it.
Reduced name space. The Singleton pattern is an improvement over global variables. It avoids polluting the name space with global
variables that store sole instances.
Permits refinement of operations and representation. The Singleton class may be subclassed, and it's easy to configure an application
with an instance of this extended class. You can configure the
application with an instance of the class you need at run-time.
Permits a variable number of instances. The pattern makes it easy to change your mind and allow more than one instance of the Singleton
class. Moreover, you can use the same approach to control the number
of instances that the application uses. Only the operation that grants
access to the Singleton instance needs to change.
More flexible than class operations. Another way to package a singleton's functionality is to useThe Singleton class can be
subclassed. class operations (that is, static member functions in C++
or class methods in Smalltalk). But both of these language techniques
make it hard to change a design to allow more than one instance
ofclass. Moreover, static member functions in C++ are never virtual,
so subclasses can't override them polymorphically.

Is it good practice to use AppDelegate for data manipulation and Handling?

I am making an object of AppDelegate and using it throughout my program, and I have declared all setters and getters, and also insert, select, delete, update queries of database in it.
I want to ask that is it a good practice to do so,
if yes, then how, and if no then why it is not a good practice?
I hope my question is clear, please ask relating questions if you have any.
It's not a good strategy to turn your AppDelegate into a "big ball of mud" that contains a million methods and properties (although it might be tempting).
A better and more object oriented approach to section off bits of functionality into well-designed objects -- for example you might have a class DatabaseManager which handles all database interactions. You might then have bits of your app which need the DatabaseManager ask the app delegate instance for a reference to a DatabaseManager.
Alternatively, you can pass around a reference to the DatabaseManager to the parts of the app that need it. This last approach does however cause more 'interface pollution', where you have to modify interfaces in lots of places in order to pass in the DatabaseManager.
And yet another alternative would be to effectively make your DatabaseManager itself be a 'singleton' -- whereby an instance of it is accessed via a class method on the class. Singletons that work in this way are often frowned upon, and usually for good reasons (makes testing harder, that sort of thing). I tend to avoid having objects have their 'singleton' nature baked right into the object -- I prefer, if I need that sort of thing, to have a known point of access (a kind of 'factory' if you like) where you can go to obtain a shared instance.
I think the best way would be creating a global singleton class instead of handling in the Appdelegate.
Declare all you setters and getters there and using the singleton object handle all around your project. See this link how to create singleton class
For Database, create a DataAccessLayerClass. whenever you want to execute any queries access this class. This class methods should have inputs as your data and will create the queries and will execute that query and return the data.
It's all about complexity and your feelings. You must like your solution ;-)
I obviously do this in another way - I've got singleton, which does handle all my common database things. I'm trying to keep application delegate as simple as possible. It's better for code sharing, etc.