2

I'm wondering how to create a default class constructor. I do not want to waste resources, so I just want the constructor to return a pointer to an already existing instance of the class.

This is what I thought of. Obviously, it doesn't work, but I want to follow this code's logic.

public Sprite()
{
  return Default.MissingSprite;
}

public Sprite(Texture2D texture, SpriteDrawMode drawMode)
{
  if (drawMode != SpriteDrawMode.Sliced) throw new ArgumentException("...");
  this.texture = texture;
  this.drawMode = drawMode;
  this.sliceFraction = Default.SpriteSliceFraction;
}

public Sprite(Texture2D texture, SpriteDrawMode drawMode, float sliceFraction)
{
  this.texture = texture;
  this.drawMode = drawMode;
  this.sliceFraction = sliceFraction;
}

I know constructors are void, so I can't return in them.

I do NOT want to just assign the values of the default instance, as that would waste memory, since it would just create a duplicate of the default instance

//This is what I do NOT want
public Sprite()
{
  this.texture = Default.MissingSprite.texture;
  this.drawMode = Default.MissingSprite.drawMode;
  this.sliceFraction = Default.MissingSprite.sliceFraction;
}

Is what I'm trying to achieve possible? Are there any design problems with my thought process?

Mravec
  • 192
  • 1
  • 12
  • 4
    Use a Factory Method to return the default instance. You can new up a default there, if one doesn't exist yet. – Robert Harvey Jun 03 '19 at 18:22
  • Read about Singleton pattern https://csharpindepth.com/articles/singleton – xneg Jun 03 '19 at 18:22
  • Can you provide a little detail about how you determined that the class in question is actually creating a memory usage problem that needs to be solved? – 15ee8f99-57ff-4f92-890c-b56153 Jun 03 '19 at 18:26
  • 1
    Is the sprite immutable, that is, once its properties are set, can they be changed? You'll need to account for that if you create and reuse a single default instance. Otherwise that instance is shared, and then one consumer could change its properties, affecting all the others. – Scott Hannen Jun 03 '19 at 18:26
  • 1
    If you already have `Default.MissingSprite`, why not just refer to that instance whereever you would call the constructor? – Blorgbeard Jun 03 '19 at 18:30
  • 1
    Don't build features that control a specific instance's lifetime into the class itself. Don't be tempted by the [singleton (anti)pattern](https://stackoverflow.com/questions/12755539/why-is-singleton-considered-an-anti-pattern). This should be controlled externally through use of (for instance) a factory method, or dependency injection. Even [`Lazy`](https://learn.microsoft.com/en-us/dotnet/api/system.lazy-1?view=netframework-4.8) can be useful for this. – spender Jun 03 '19 at 18:33

1 Answers1

0

You want to do two operations, one is to create an instance and the other is to return some value Default.MissingSprite. This is not possible in C#.


What you should do is create a property which addresses the state and holds that value such as

public SpriteState State { get; set;}

Then upon creation (like you have in your example)

public Sprite()
{
   State = Default.MissingSprite;
} 

Then set other States in the other constructors as appropriate.

Finally it is up to the user to check the State property before usage.

var mySprite = new Sprite();

// Some code which could change the State...

switch (mySprite.State)
{
   case Default.MissingSprite:
      ...
   break;

   case Default.OkSprite:
      ...
   break;
  ...
ΩmegaMan
  • 29,542
  • 12
  • 100
  • 122