Simple worker class program I Have written this program to add workers into a list and print them. I'd like a review of this. I'm especially concerned if the method Addworker should be inside the class or in the main program.

Person:

class Person
{
    public uint NumberId;
    public string Name;
    public string LastName;
    public uint Age; // Age Should Be Beetween 18 And 40

    public uint numberId
    {
        set { this.NumberId = value; }
        get { return this.NumberId; }
    }

    public string name
    {
        set { this.Name = value; }
        get { return this.Name; }
    }

    public string lastName
    {
        set { this.LastName = value; }
        get { return this.LastName; }
    }

    public uint age
    {
        set
        {
            if (value &lt; 18 || value &gt; 40)
            {
                throw new ArgumentOutOfRangeException();
            }
            this.Age = value;
        }

        get { return this.Age; }
    }
}


Worker:

class Worker:Person
{
    private uint WageHour;
    private uint Total_Hours;

    public uint wageHour
    {
        set { this.WageHour = value; }
        get { return this.WageHour; }
    }

    public uint total_Hours
    {
        set { this.Total_Hours = value; }
        get { return this.Total_Hours; }
    }

    public double SalaryCalcul()
    {
        return this.wageHour * this.total_Hours;
    }

    public override string ToString()
    {
        return string.Format("Name : {0} Last Name : {1} Age : {2} WageHour : {3} Total Hours : {4} Salary : {5}",
                          this.name,this.lastName,this.age,this.wageHour,this.total_Hours,this.SalaryCalcul().ToString());

     }
}


Main program:

class Program
{
    static List&lt;Worker&gt; WorkersList = new List&lt;Worker&gt;();

    static void Main(string[] args)
    {
        do
        {
            Console.Clear();

            Console.WriteLine("1 - Add A Worker .");
            Console.WriteLine("2 - Print List .");

            int Choice = int.Parse(Console.ReadLine());

            switch (Choice)
            {
                case 1:
                    {
                        AddWorker();
                        break;
                    }

                case 2:
                    {
                        Console.Clear();

                        foreach (Worker W in WorkersList)
                        {
                            Console.WriteLine(W.ToString());
                        }

                        Console.ReadKey();

                        break;
                    }
            }
        } 
        while (true);

    }

    static void AddWorker()
    {
        Worker W = new Worker();

        Console.WriteLine("Enter ID : ");
        W.numberId = uint.Parse(Console.ReadLine());

        Console.WriteLine("Enter Name : ");
        W.name = Console.ReadLine();

        Console.WriteLine("Enter Last Name : ");
        W.lastName = Console.ReadLine();

        try
        {
            Console.WriteLine("Enter Age : ");
            W.age = uint.Parse(Console.ReadLine());
        }
        catch (Exception)
        {
            Console.WriteLine("Age Should Be Between 18 and 40 ");
        }

        Console.WriteLine("Enter Hour Wage : ");
        W.wageHour = uint.Parse(Console.ReadLine());

        Console.WriteLine("Enter Total Hours : ");
        W.total_Hours = uint.Parse(Console.ReadLine());

        WorkersList.Add(W);
    }
}
Properties

Currently, you're defining a public field, and then creating a property which can get and set that public field, like this:


public int SomeNumber;
public int SomeNumberProperty
{
     get { return this.SomeNumber; }
     set { this.SomeNumber = value; }
}



Firstly, the field that the property sets and gets should be private, if you choose to not use auto-properties, like this:

private int _SomeNumber;
public int SomeNumberProperty
{
    get { return this._SomeNumber; }
    set { this._SomeNumber = value; }
}


Now, while this is something that you can do, in the case of your code, there is no need to manually define the getters and setters in your properties. You can simply define an auto-property, like this:

public int SomeNumber { get; set; }


The C# compiler will automatically generate a private field in which the value for the property is stored. Do note, this value can only be accessed through the property's getters and setters.

If you're using C# 6 or later, you can also define a default value for the property, like this:

public int SomeNumber { get; set; } = 42;




Constructors

All of your classes that represent something, like a Person or a Worker are missing something rather important - a constructor. A constructor allows you to initialize the values of specific properties or fields when the object is instantiated. For example, here's a representation of a Person class using auto-properties and a constructor:

public class Person
{
    public int Age { get; set; }
    public string Name { get; set; }

    public Person(int age, string name)
    {
        this.Age = age;
        this.Name = name;
    }
}


The constructor in question is this portion of code right here:


public Person(int age, string name)
{
    this.Age = age;
    this.Name = name;
}



It should be relatively self-explanatory what this chunk of code is doing. It's called when an instance of Person is created and sets the value of each property to the corresponding argument passed. An example of creating a new instance of this class might look like this:

Person person1 = new Person(42, "Bill");


By using the constructor to initialize values, it means that you don't have to initialize properties/fields like this:

Person person1 = new Person();
person1.Age = 42;
person1.Name = "Bill";


Side note: You can also use the object initializer syntax instead of constructors, but I'd recommend sticking with constructors for now.



Other nitpicks

The following method is the perfect candidate to be converted into a property:


public double SalaryCalcul()
{
    return this.wageHour * this.Total_Hours;
}



All this method does is return a value, so we can define a property like this:

public double Salary
{
    get { return this.wagehour * this.Total_Hours; }
}


If you are using a C# 6 or later, you can simply write the above like this:

public double Salary =&gt; this.wagehour * this.Total_Hours;


Simply attempting to convert user input to an integer isn't the best idea. What if the user enters a string, like "Hello"? To ensure that no errors are caused due to faulty user data, you should set up something like this:

int convertedUserInput;
string userInput = Console.ReadLine();

if(Int32.TryParse(userInput, out convertedUserInput))
{
    // the user entered a proper integer
}
else
{
    // the user did not enter a proper integer
}


As a side note, properties should also be named in PascalCase, along with fields.