The Main() Method in C#


The Main() method is an entry point of console and windows applications on the .NET or .NET Core platform. It is also an entry of ASP.NET Core web applications.

When you run an application, it starts the execution from the Main() method. So, a program can have only one Main() method as an entry point. However, a class can have multiple Main() methods, but any one of them can be an entry point of an application.

The Main() method can be defined in various ways. The following are the valid signatures of the Main() method.

Main() Method Signatures for Entry Point
//parameterless Main() methods
public static void Main() { }
public static int Main() { }
public static async Task Main() { }
public static async Task<int> Main() { }

//Main() methods with string[] parameter
public static void Main(string[] args) { }
public static int Main(string[] args) { }
public static async Task Main(string[] args) { }
public static async Task<int> Main(string[] args) { }

The following is the default Main() method of a console application.

Example: Main() Method
class Program
{
    static void Main(string[] args)
    {
        //program execution starts from here
        Console.WriteLine("Command line Arguments: {0}", args.length)
    }
}

In the above example, the exection of a console application starts from the Main() method. The string[] args parameter contains values passed from the command-line while executing an application from the command prompt/terminal. Learn how to pass the command-line arguments to C# console application.

Note that no other type of parameters can be included in the Main() method. For example, the following will throw Program class does not contain a static Main() method suitable for an entry point error.

Invalid Main() Methods As Entry Point
static void Main(string args) {

}

static void Main(string[] args, int id) {

}

static void Main(bool isStarting) {

}

Starting from C# 9 (.NET 5), you can use the top-level statements feature to omit the Main() method. However, you can write top-level statements in one cs file only.

Example: Top-level Statements as Entry Point in C# 9
using System;

Console.WriteLine("This is considered as an entry point");

Parameterless Main() Method

The Main() method can be parameterless if you are not going to pass any command-line arguments. For example, the following is a valid Main() method as an entry point.

Example: Parameterless Main() Method
class Program
{
    static void Main()
    {
        //program execution starts from here
    }
}

Return Type of the Main() Method

The Main() method can have a void, int, Task, or Task<int> as a return type. Returning int or Task<int> communicates status information to programs that started the execution. Returning 0 from the Main() will communicate success, and returning non-zero will communicate failure.

Example:
static int Main(string[] args)
{

    //indicates success
    return 0;
}

static int Main(string[] args)
{

    //indicates failure
    return 1;
}

Asynchronous Main Method

The Main() method can also be asynchronous using the async keyword. The return type of async Main() methods can be Task or Task<int>.

Example: Asynchronous Main() Methods
//Use of Task return type in the Main() method
public static async Task Main()
{

}

public static async Task Main(string[] args)
{

}

public static async Task<int> Main()
{

}

public static async Task<int> Main(string[] args)
{

}

Overloading of the Main Method

The Main() method can be overloaded for different purposes. However, a class or a struct can only have one valid Main() method signature as an entry point; other Main() methods can use other signatures, as shown below.

Example: Overloading of Main() Method
class Program
{
    //entry point
    static void Main()
    {
        Console.WriteLine("This is the entry point");
        Main(10);
    }

    //overload Main method
    static void Main(int a)
    {
        Console.WriteLine(a);
        Main(10, 20);
    }

    //overload Main method
    static void Main(int a, int b)
    {
        Console.WriteLine(a, b);
    }
}

The following example shows the invalid overloading of the Main() method because a class contains two valid signatures of the Main() method as an entry point.

Error: Can't have multiple Main() entry point
class Program
{
    //can't have multiple valid Main() entry points
    //valid entiry point
    static void Main(string[] args)
    {
    }

    //valid entry point
    static void Main()
    {
    }
}

Configure Startup Object

If multiple classes have valid Main() methods, then you can configure any one of them as an entry point using an application's Startup Object property.

Example: Multiple Main() Methods
namespace MainMethodDemo
{
    class Program
    {
        static void Main(string[] args)
        {
            Console.WriteLine("Program.Main() Entry Point");
        }
    }

    class WindowProgram
    {
        static void Main(string[] args)
        {
            Console.WriteLine("WindowProgram.Main() Entry Point");
        }
    }
}

In the above example, two classes contain the valid Main() methods. To specify which Main() method should be an entry point, right-click on your project node in the solution explorer and click on Properties. Then, in the Properties page and Application tab, select the class name in the Startup Object dropdown of which the Main() method should be invoked, as shown below.

Configure Startup Object

Summary:

  • The Main() method is an entry point of an executable program where the program execution begins and ends.
  • It can be declared as a public, private, protected, or internal access modifier.
  • The method name must be Main(). It cannot be any other name.
  • It must be static and declared inside a class or a struct.
  • It can have string[] type parameter only.
  • Return type can be a void, int, Task, or Task<int>.
  • The Main() method cannot be overridden and cannot be declared as virtual or abstract.
  • Multiple Main() methods are allowed, but only one method can be configured as an entry point.
  • In the case of Windows applications, the input parameter can be added manually, or the GetCommandLineArgs() method can be used to get the command-line arguments.
  • The Main() method can be omited in C# 9 (.NET 5) by using top-level statements in a class.