C# Fundamentals: From Your First Program to Async and JSON · C# Basics: Types, Collections, Classes and Pattern Matching

Hello, C#: The dotnet CLI, Types and Strings

Create and run a C# project with the dotnet CLI, use top-level statements, declare typed variables, build strings with interpolation and format specifiers, and understand value versus reference types.

Create a free account to save this page, take notes and track your progress. Sign in

What you'll build

A small invoice printer: typed variables for items, quantities and prices, a total with tax, and neatly formatted output using string interpolation and format specifiers.

The idea

C# is a modern, strongly typed language from Microsoft that runs on .NET on Windows, Linux and macOS. It is used for web APIs (ASP.NET Core), desktop and mobile apps, games (Unity), cloud services and tools.

Create and run a project with the dotnet CLI:

dotnet new console -n Invoice   # creates Invoice.csproj and Program.cs
cd Invoice
dotnet run                      # builds and runs

Modern projects use top-level statements: Program.cs can be just statements, with no Main method or class required, and implicit usings import common namespaces such as System and System.Linq.

Core ideas:

  • Types: int, long, double, decimal (exact decimal arithmetic, for money), bool, char, string. var infers the type from the right side: var count = 3; is still an int and still strongly typed.
  • Value types (int, double, bool, structs) are copied on assignment. Reference types (string, classes, arrays) are references to objects. string is immutable: operations return new strings.
  • Interpolation: $"{name} owes {total:C}" embeds expressions. Format specifiers go after a colon: :C currency, :N2 two decimals with separators, :P1 percent, :D5 zero-padded integers, :yyyy-MM-dd for dates.
  • Constants and readonly data: const for compile-time constants.

The code

An invoice with decimal, interpolation and format specifiers
using System.Globalization;

CultureInfo.CurrentCulture = CultureInfo.InvariantCulture;   // make the output identical on every machine

const decimal TaxRate = 0.2m;                // the m suffix makes a decimal literal
var customer = "Corner Cafe";
var items = new[] { ("Coffee beans", 3, 12.50m), ("Filter papers", 2, 3.20m), ("Mugs", 6, 4.75m) };

Console.WriteLine($"Invoice for {customer}");
Console.WriteLine(new string('-', 40));

decimal subtotal = 0;
foreach (var (name, quantity, price) in items)
{
    var line = quantity * price;
    subtotal += line;
    Console.WriteLine($"{name,-15} {quantity,3} x {price,6:N2} = {line,8:N2}");
}

var tax = subtotal * TaxRate;
var total = subtotal + tax;
Console.WriteLine(new string('-', 40));
Console.WriteLine($"{"Subtotal",-28} {subtotal,8:N2}");
Console.WriteLine($"{"Tax (" + TaxRate.ToString("P0") + ")",-28} {tax,8:N2}");
Console.WriteLine($"{"Total",-28} {total,8:N2}");

// double is fast but approximate; decimal is exact for money
Console.WriteLine(0.1 + 0.2 == 0.3);          // False
Console.WriteLine(0.1m + 0.2m == 0.3m);       // True

// Strings are immutable: methods return new strings
var shout = customer.ToUpper();
Console.WriteLine($"{customer} -> {shout}, length {customer.Length}, id {42:D5}");

Output

Invoice for Corner Cafe
----------------------------------------
Coffee beans      3 x  12.50 =    37.50
Filter papers     2 x   3.20 =     6.40
Mugs              6 x   4.75 =    28.50
----------------------------------------
Subtotal                        72.40
Tax (20 %)                      14.48
Total                           86.88
False
True
Corner Cafe -> CORNER CAFE, length 11, id 00042

Run this on your computer — see “Get Started” for setup.

Notice the alignment: {name,-15} left-aligns in 15 characters and {line,8:N2} right-aligns a number in 8 characters with 2 decimals.

Common mistakes

  • Using double for money. Binary floating point can't represent 0.1 exactly; use decimal.
  • Forgetting that string is immutable. name.ToUpper(); alone does nothing; assign the result.
  • Concatenating strings in loops (s += x). Use StringBuilder or string.Join for many parts.
  • Relying on the machine's culture for number formatting. Pass CultureInfo.InvariantCulture for data, and the user's culture for display.
  • Confusing integer division: 7 / 2 is 3; make one side double or decimal.

Key points

  • dotnet new console and dotnet run create and run a project; top-level statements remove boilerplate.
  • var infers the type; it is still statically typed. Use decimal for money.
  • Interpolated strings ($"...") support alignment (,10) and format specifiers (:N2, :C, :P1).
  • Value types are copied, reference types are shared, and strings are immutable.

Further reading: A tour of C#.

Practice questions

Why use `decimal` instead of `double` for money?

Answer

decimal stores base-10 numbers exactly, so 0.1m + 0.2m == 0.3m. double is binary floating point and cannot represent many decimal fractions exactly, which causes rounding errors in financial calculations.

What does `$"{price,8:N2}"` do?

Answer

It inserts price right-aligned in a field 8 characters wide (the comma sets alignment) and formats it as a number with thousands separators and 2 decimal places (the N2 specifier after the colon).

Open in the app to mark lessons complete, take notes and track your progress.

Was this page helpful?