DEV Community

Cover image for How to get rid of the `new` C# keyword
KiritchoukC
KiritchoukC

Posted on

How to get rid of the `new` C# keyword

Why would I do that?

I recently started a new personal project following the DDD approach.

If you strictly follow the DDD rules, you need to create a new class for each property.
And initializing those classes can quickly become a burden.

Example:

var person = new Person(
  new PersonId(1), 
  new PersonFirstName("Clément"), 
  new PersonLastName("Kiritchouk"),
  new PersonBirthYear(1994))
Enter fullscreen mode Exit fullscreen mode

There's a way to save a few keystrokes, increase readability and make chaining easier.

Static constructors obviously

Disclaimer: This is my way of doing this, feel free to adapt or improvre

First, Create a static partial Constructors class like this:

// Constructors.cs
public static partial class Constructors
{

}
Enter fullscreen mode Exit fullscreen mode

I use this class for System classes (DateTime, List, ...)
I'll add some interesting ones later on...

Then create another static partial Constructors class where I put all my Person constructors.

// Constructors.Person.cs
public static partial class Constructors
{
  public static PersonId PersonId(int id) => new PersonId(id);
  public static PersonFirstName PersonFirstName(string firstName) => new PersonFirstName(firstName);
  public static PersonLastName PersonLastName(string lastName) => new PersonLastName(lastName);
  public static PersonBirthYear PersonBirthYear(int year) => new PersonBirthYear(year);

  public static Person Person(PersonId id, PersonFirstName firstName, PersonLastName lastName, PersonBirthYear year)
    => new Person(PersonId(id), PersonFirstName(firstName), PersonLastName(lastName), PersonBirthYear(year));
}
Enter fullscreen mode Exit fullscreen mode

And Done!

How to use it

It's refactoring time. Now we can initialize a Person class like this.
Actually, it's easy... Just drop the new keyword.

Don't forget the static using!

using static MyAwesomeProject.Constructors

var person = Person(
  PersonId(1), 
  PersonFirstName("Clément"), 
  PersonLastName("Kiritchouk"),
  PersonBirthYear(1994))
Enter fullscreen mode Exit fullscreen mode

Bonus

Ok, maybe you're not convinced yet.
Let's create a list of persons

var persons = new List<Person>{
  person1,
  person2,
  person3
};
Enter fullscreen mode Exit fullscreen mode

Why not create a constructor for initializing List?
Update your Constructors.cs file like this:

// Constructors.cs
public static partial class Constructors
{
  public static List<T> List<T>(params T[] items) => new List<T>(items);
}
Enter fullscreen mode Exit fullscreen mode

Now you can do

var persons = List(person1,person2,person3);
Enter fullscreen mode Exit fullscreen mode

You don't have to specify the type anymore because the type system infers it.

Cons

Well, there are some cons using this technique.

  • You have to create a constructor for every type while new is built-in.
  • It's unusual, other developers might be confused looking at your code.

Anyway, I like it and I had to share it with you. Please tell me what are your thoughts on this. 😏

Discussion (5)

Collapse
mrpmorris profile image
Peter Morris

Might be better to have implicit conversion from string/int to the property type, but not from the property type back.

Collapse
kiritchoukc profile image
KiritchoukC Author

Maybe I didnt get it right but if you do that you won't get type checking anymore.
Because then a string can convert to a Name or a FirstName.

Collapse
mrpmorris profile image
Peter Morris

Yes it can, but you can just as easily pass the wrong string value to your constructor.

It's not string to FirstName you are trying to prevent, it is FirstName to LastName.

Collapse
_siva_sankar profile image
Siva Sankaran S

Why do we need to get rid of new keyword ? The approach show here seems to be a syntactic sugar. Do this approach increase readability of code ?

Collapse
kiritchoukc profile image
KiritchoukC Author

Why do we need to get rid of new keyword ?
You don't need to. And you should not if you don't see any benefit.

The approach show here seems to be a syntactic sugar.
That's 100% syntactic sugar.

Do this approach increase readability of code ?
Readability is subjective.
You might be confused the first time you see this.
But then, it feels like the code is less noisy and cluttered with useless keyword and types