11

below is a sample class,

public class Loan
{
}

now, what is difference between these below 2 line and what is difference between them?

Loan loan = default(Loan);
Loan loan = new Loan();

Is there preference to use one over other?

user2994834
  • 387
  • 1
  • 4
  • 14

4 Answers4

20

default is used for zeroing out values. For reference types, thats null. For value types, that is effectively the same as using new without any arguments. default is great for generics.

new creates an instance of that type, invoking the constructor.

In your example, if I do:

Loan loan = default(Loan);

or in newer versions of C#:

Loan loan = default;

which is logically equivalent to

Loan loan = null;

you will get a null reference exception if you don't construct it:

loan.MakePayment(100); // Throws
Daniel A. White
  • 187,200
  • 47
  • 362
  • 445
  • You might want to update this answer: since C# 10, it's legal to write an explicit default constructor for structs, so new and default are no longer the same thing for a struct. – Thomas Levesque Jun 18 '23 at 19:21
6

UPDATE: as of C# 10, it's possible to declare an explicit default constructor for a struct, which makes my original answer incorrect.

  • For value types (i.e. structs) with no explicit default constructor, default(T) and new T() are effectively the same: they both return an uninitialized instance of T.
  • For value types with an explicit default constructor, default(T) returns an uninitialized instance, whereas new T() returns a new instance of T, initialized with the default constructor.
  • For reference types, default(T) returns null, whereas new T() returns a new instance of T, initialized with the default constructor.

In your code, Loan is a class, so default(Loan) returns null.


ORIGINAL ANSWER - no longer true since C# 10.

For value types (i.e. structs), default(T) and new T() are effectively the same: they both return an uninitialized instance of T. For reference types, however, default(T) returns null, while new T() returns a new instance of T, initialized with the default constructor.

In your code, Loan is a class, so default(Loan) returns null.

Thomas Levesque
  • 286,951
  • 70
  • 623
  • 758
  • I'm not actually sure this is true. If you create a struct with three ints in it and a default constructor that sets them to 1, 2, 3, I'm pretty sure default will still give you a struct full of zeros, where new() will give you 1, 2, 3. – PreventRage Jun 18 '23 at 04:02
  • 1
    @PreventRage indeed. It *used* to be true, because writing an explicit default constructor for a struct was not allowed, but now it is. I'll update my answer. – Thomas Levesque Jun 18 '23 at 19:13
5

default would return the default value for value types and null for reference type.

If your Load is a class, first line would return null, whereas second line would return a new instance of Loan

Loan loan = default(Loan); // null if Loan is a reference type
Loan loan = new Loan(); // new instance of Loan - Not Null

If Loan is a struct (or a value type) then both of the above (default and new) would be same.

Habib
  • 219,104
  • 29
  • 407
  • 436
1

In generic classes and methods, one issue that arises is how to assign a default value to a parameterized type T when you do not know the following in advance:

Whether T will be a reference type or a value type.

If T is a value type, whether it will be a numeric value or a struct.

Given a variable t of a parameterized type T, the statement t = null is only valid if T is a reference type and t = 0 will only work for numeric value types but not for structs. The solution is to use the default keyword, which will return null for reference types and zero for numeric value types. For structs, it will return each member of the struct initialized to zero or null depending on whether they are value or reference types. For nullable value types, default returns a System.Nullable, which is initialized like any struct.

In C#, the new keyword can be used as an operator, a modifier, or a constraint.

new Operator

Used to create objects and invoke constructors.

new Modifier

Used to hide an inherited member from a base class member.

new Constraint

Used to restrict types that might be used as arguments for a type parameter in a generic declaration.
Ali.Rashidi
  • 1,284
  • 4
  • 22
  • 51