// Types used in the examples below

public interface IMyService {}
public class MyService : IMyService {}

public interface IMyService<T> {}
public class MyService<T> : IMyService<T> {}

Registering an object instance

Registering an object instance is always a singleton, by definition.

ServiceLocator.Register(new MyService());
IMyService svc1 = ServiceLocator.Get<IMyService>();
// svc1 = the instance that was registered above

IMyService svc2 = ServiceLocator.Get<IMyService>();
// svc2 = the instance that was registered above (same as svc1)

Registering a type as a singleton

Registering a a type is by default a transient dependency. It can be made a singleton by appending .Singleton() after the Register() call.

IMyService svc1 = ServiceLocator.Get<IMyService>();
// svc1 = a new instance of MyService

IMyService svc2 = ServiceLocator.Get<IMyService>();
// svc2 = same instance as svc1

Singletons and open generics

When an open generic type is registered and configured to be a singleton, a new object will be created for each combination of types used with the open generic type.

var svc1 = ServiceLocator.Get<IMyService<int>>();
var svc2 = ServiceLocator.Get<IMyService<string>>();
var svc3 = ServiceLocator.Get<IMyService<int>>();

// svc1 = instance of MyService<int>
// svc2 = instance of MyService<string>
// svc3 = same instance as svc1