Skip to content
Merged
Show file tree
Hide file tree
Changes from 2 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 4 additions & 1 deletion docs/csharp/fundamentals/program-structure/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -12,10 +12,13 @@ C# programs consist of one or more files. Each file contains zero or more namesp

:::code language="csharp" source="snippets/toplevel-structure/Program.cs":::

The preceding example uses [*top-level statements*](top-level-statements.md) for the program's entry point. Only one file can have top-level statements. The program's entry point is the first line of program text in that file. You can also create a static method named [`Main`](main-command-line.md) as the program's entry point, as shown in the following example:
The preceding example uses [*top-level statements*](top-level-statements.md) for the program's entry point. Only one file can have top-level statements. The program's entry point is the first line of program text in that file. In this case, it's the `Console.WriteLine("Hello world!");`.
You can also create a static method named [`Main`](main-command-line.md) as the program's entry point, as shown in the following example:

:::code language="csharp" source="snippets/structure/Program.cs":::

In that case the program will start in the first line of `Main` method, which is `Console.WriteLine("Hello world!");`

## Related Sections

You learn about these program elements in the [types](../types/index.md) section of the fundamentals guide:
Expand Down
13 changes: 11 additions & 2 deletions docs/csharp/fundamentals/program-structure/main-command-line.md
Original file line number Diff line number Diff line change
Expand Up @@ -17,12 +17,14 @@
The `Main` method is the entry point of a C# application. When the application is started, the `Main` method is the first method that is invoked.

There can only be one entry point in a C# program. If you have more than one class that has a `Main` method, you must compile your program with the **StartupObject** compiler option to specify which `Main` method to use as the entry point. For more information, see [**StartupObject** (C# Compiler Options)](../../language-reference/compiler-options/advanced.md#mainentrypoint-or-startupobject).
<br/>Below is the example which first line executed will display the number of command line arguments:

:::code language="csharp" source="snippets/main-command-line/TestClass.cs":::

You can also use Top-level statements in one file as the entry point for your application.
Just as the `Main` method, top-level statements can also [return values](#main-return-values) and access [command-line arguments](#command-line-arguments).
For more information, see [Top-level statements](top-level-statements.md).
<br/>The following example uses `foreach` loop to display the command line arguments using the args variable, and at the end of the program returns a success code (`0`):

:::code language="csharp" source="snippets/top-level-statements-1/Program.cs":::

Expand Down Expand Up @@ -84,6 +86,8 @@

:::code language="csharp" source="snippets/main-command-line/MainReturnValTest.cs":::

Remember to save this program as *MainReturnValTest.cs*.

When a program is executed in Windows, any value returned from the `Main` function is stored in an environment variable. This environment variable can be retrieved using `ERRORLEVEL` from a batch file, or `$LastExitCode` from PowerShell.

You can build the application using the [dotnet CLI](../../../core/tools/dotnet.md) `dotnet build` command.
Expand Down Expand Up @@ -122,7 +126,6 @@

private static async Task<int> AsyncConsoleWork()
{
// Main body here
return 0;
}
}
Expand All @@ -132,6 +135,8 @@

:::code language="csharp" source="snippets/main-arguments/Program.cs" id="AsyncMain":::

In both examples main body of the program is within the body of `AsyncConsoleWork()` method.

An advantage of declaring `Main` as `async` is that the compiler always generates the correct code.

When the application entry point returns a `Task` or `Task<int>`, the compiler generates a new entry point that calls the entry point method declared in the application code. Assuming that this entry point is called `$GeneratedMain`, the compiler generates the following code for these entry points:
Expand Down Expand Up @@ -205,19 +210,23 @@

:::code language="csharp" source="./snippets/main-command-line/Factorial.cs":::

At the beginning of the `Main` method the program tests if input arguments were not supplied comparing length of `args` argument to `0` and displays the help if no argument are found.
<br/>If arguments are provided (`args.Length` is greater than 0) program tries to convert the input arguments to numbers. This will throw an exception if the argument is not a number.
<br/>After factorial is calculated (stored in `result` variable of type `long`) the verbose result is printed depending on the `result` variable.

2. From the **Start** screen or **Start** menu, open a Visual Studio **Developer Command Prompt** window, and then navigate to the folder that contains the file that you created.

Check failure on line 217 in docs/csharp/fundamentals/program-structure/main-command-line.md

View workflow job for this annotation

GitHub Actions / lint

Ordered list item prefix

docs/csharp/fundamentals/program-structure/main-command-line.md:217:1 MD029/ol-prefix Ordered list item prefix [Expected: 1; Actual: 2; Style: 1/2/3] https://github.com/DavidAnson/markdownlint/blob/v0.37.2/doc/md029.md

3. Enter the following command to compile the application.

Check failure on line 219 in docs/csharp/fundamentals/program-structure/main-command-line.md

View workflow job for this annotation

GitHub Actions / lint

Ordered list item prefix

docs/csharp/fundamentals/program-structure/main-command-line.md:219:1 MD029/ol-prefix Ordered list item prefix [Expected: 2; Actual: 3; Style: 1/2/3] https://github.com/DavidAnson/markdownlint/blob/v0.37.2/doc/md029.md

`dotnet build`

If your application has no compilation errors, an executable file that's named *Factorial.exe* is created.

4. Enter the following command to calculate the factorial of 3:

Check failure on line 225 in docs/csharp/fundamentals/program-structure/main-command-line.md

View workflow job for this annotation

GitHub Actions / lint

Ordered list item prefix

docs/csharp/fundamentals/program-structure/main-command-line.md:225:1 MD029/ol-prefix Ordered list item prefix [Expected: 3; Actual: 4; Style: 1/2/3] https://github.com/DavidAnson/markdownlint/blob/v0.37.2/doc/md029.md

`dotnet run -- 3`

5. The command produces this output: `The factorial of 3 is 6.`
5. If 3 is entered on command line as the program's argument, the output reads: `The factorial of 3 is 6.`

Check failure on line 229 in docs/csharp/fundamentals/program-structure/main-command-line.md

View workflow job for this annotation

GitHub Actions / lint

Ordered list item prefix

docs/csharp/fundamentals/program-structure/main-command-line.md:229:1 MD029/ol-prefix Ordered list item prefix [Expected: 4; Actual: 5; Style: 1/2/3] https://github.com/DavidAnson/markdownlint/blob/v0.37.2/doc/md029.md

> [!NOTE]
> When running an application in Visual Studio, you can specify command-line arguments in the [Debug Page, Project Designer](/visualstudio/ide/reference/debug-page-project-designer).
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,6 @@ static async Task<int> Main(string[] args)

private static async Task<int> AsyncConsoleWork()
{
// main body here
return 0;
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,17 +22,13 @@ class MainClass
{
static int Main(string[] args)
{
// Test if input arguments were supplied.
if (args.Length == 0)
{
Console.WriteLine("Please enter a numeric argument.");
Console.WriteLine("Usage: Factorial <num>");
return 1;
}

// Try to convert the input arguments to numbers. This will throw
// an exception if the argument is not a number.
// num = int.Parse(args[0]);
int num;
bool test = int.TryParse(args[0], out num);
if (!test)
Expand All @@ -42,10 +38,8 @@ static int Main(string[] args)
return 1;
}

// Calculate factorial.
long result = Functions.Factorial(num);

// Print result.
if (result == -1)
Console.WriteLine("Input must be >= 0 and <= 20.");
else
Expand All @@ -54,6 +48,3 @@ static int Main(string[] args)
return 0;
}
}
// If 3 is entered on command line, the
// output reads: The factorial of 3 is 6.

Original file line number Diff line number Diff line change
@@ -1,4 +1,3 @@
// Save this program as MainReturnValTest.cs.
class MainReturnValTest
{
static int Main()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,6 @@
{
static void Main(string[] args)
{
// Display the number of command line arguments.
Console.WriteLine(args.Length);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,6 @@ class Program
{
static void Main(string[] args)
{
//Your program starts here...
Console.WriteLine("Hello world!");
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,13 +3,11 @@
StringBuilder builder = new();
builder.AppendLine("The following arguments are passed:");

// Display the command line arguments using the args variable.
foreach (var arg in args)
{
builder.AppendLine($"Argument={arg}");
}

Console.WriteLine(builder.ToString());

// Return a success code.
return 0;
Original file line number Diff line number Diff line change
@@ -1,7 +1,5 @@
// A skeleton of a C# program
using System;
using System;

// Your program starts here:
Console.WriteLine("Hello world!");

namespace YourNamespace
Expand Down
Loading