diff --git a/2-csharp/2-projects/LICENSE b/2-csharp/2-projects/LICENSE
deleted file mode 100644
index 2080d95..0000000
--- a/2-csharp/2-projects/LICENSE
+++ /dev/null
@@ -1,21 +0,0 @@
-MIT License
-
-Copyright (c) 2023 Microsoft Learning
-
-Permission is hereby granted, free of charge, to any person obtaining a copy
-of this software and associated documentation files (the "Software"), to deal
-in the Software without restriction, including without limitation the rights
-to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
-copies of the Software, and to permit persons to whom the Software is
-furnished to do so, subject to the following conditions:
-
-The above copyright notice and this permission notice shall be included in all
-copies or substantial portions of the Software.
-
-THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
-IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
-FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
-AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
-LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
-OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
-SOFTWARE.
diff --git a/2-csharp/2-projects/README.md b/2-csharp/2-projects/README.md
deleted file mode 100644
index 139866e..0000000
--- a/2-csharp/2-projects/README.md
+++ /dev/null
@@ -1,2 +0,0 @@
-# Guided-project-branching-looping-CSharp
-Starter and Solution code for the Guided project: "Develop conditional branching and looping structures in C#" from the Microsoft Learn collection "Getting started with C#"
diff --git a/2-csharp/README.md b/2-csharp/README.md
index d4fa476..283f3bd 100644
--- a/2-csharp/README.md
+++ b/2-csharp/README.md
@@ -7,10 +7,10 @@ If you're completely new to C# and want a more comprehensive learning path, chec
| | Lesson | Guided Project | Challenge Project |
| :-: | :------------------------------------------------------: | ----------------------------------------------------------------------------------------------------------------------------------- | :----------------------------------------------------------------------------------------------------------------------------: |
| 01 | [Write your first code using C#](https://learn.microsoft.com/training/paths/get-started-c-sharp-part-1/) | [Calculate and print student grades](https://learn.microsoft.com/en-us/training/modules/guided-project-calculate-print-student-grades/) | [Calculate final GPA](https://learn.microsoft.com/en-us/training/modules/guided-project-calculate-final-gpa/)
-| 02 | [Create and run simple C# console applications](https://learn.microsoft.com/training/paths/get-started-c-sharp-part-2/) | [Develop foreach and if-elseif-else structures to process array data in C#](https://learn.microsoft.com/training/modules/guided-project-arrays-iteration-selection/), [Code](1-projects/guided-project) | [Develop foreach and if-elseif-else structures to process array data in C#](https://learn.microsoft.com/training/modules/challenge-project-arrays-iteration-selection/), [Code](1-projects/challenge-project)
-| 03 | [Add logic to C# console applications](https://learn.microsoft.com/training/paths/get-started-c-sharp-part-3/) | [Develop conditional branching and looping structures in C#](https://learn.microsoft.com/training/modules/guided-project-develop-conditional-branching-looping/), [Code](2-projects/projects) | [Develop branching and looping structures in C#](https://learn.microsoft.com/training/modules/challenge-project-develop-branching-looping-structures-c-sharp/), [Code]()
-| 04 | [Work with variable data in C# console applications](https://learn.microsoft.com/training/paths/get-started-c-sharp-part-4/) | [Work with variable data in C#](https://learn.microsoft.com/training/modules/guided-project-work-variable-data-c-sharp/), [Code]() | [Challenge - Work with variable data in C#](https://learn.microsoft.com/training/modules/challenge-project-work-variable-data-c-sharp/), [Code]()
-| 05 | [Create methods in C# console applications](https://learn.microsoft.com/training/paths/get-started-c-sharp-part-5/) | [Plan a petting zoo visit](https://learn.microsoft.com/training/modules/guided-project-visit-petting-zoo/), [Code]() | [Create a mini-game](https://learn.microsoft.com/training/modules/challenge-project-create-mini-game/), [Code]()
+| 02 | [Create and run simple C# console applications](https://learn.microsoft.com/training/paths/get-started-c-sharp-part-2/) | [Develop foreach and if-elseif-else structures to process array data in C#](https://learn.microsoft.com/training/modules/guided-project-arrays-iteration-selection/), [Code](lesson-2-projects/guided-project) | [Develop foreach and if-elseif-else structures to process array data in C#](https://learn.microsoft.com/training/modules/challenge-project-arrays-iteration-selection/), [Code](lesson-2-projects/challenge-project)
+| 03 | [Add logic to C# console applications](https://learn.microsoft.com/training/paths/get-started-c-sharp-part-3/) | [Develop conditional branching and looping structures in C#](https://learn.microsoft.com/training/modules/guided-project-develop-conditional-branching-looping/), [Code](lesson-3-projects/guided-project) | [Develop branching and looping structures in C#](https://learn.microsoft.com/training/modules/challenge-project-develop-branching-looping-structures-c-sharp/), [Code](lesson-3-projects/challenge-project)
+| 04 | [Work with variable data in C# console applications](https://learn.microsoft.com/training/paths/get-started-c-sharp-part-4/) | [Work with variable data in C#](https://learn.microsoft.com/training/modules/guided-project-work-variable-data-c-sharp/), [Code](lesson-4-projects/guided-project) | [Challenge - Work with variable data in C#](https://learn.microsoft.com/training/modules/challenge-project-work-variable-data-c-sharp/), [Code](lesson-4-projects/challenge-project)
+| 05 | [Create methods in C# console applications](https://learn.microsoft.com/training/paths/get-started-c-sharp-part-5/) | [Plan a petting zoo visit](https://learn.microsoft.com/training/modules/guided-project-visit-petting-zoo/), No project files | [Create a mini-game](https://learn.microsoft.com/training/modules/challenge-project-create-mini-game/), [Code](lesson-5-projects/challenge-project)
| 06 | [Debug C# console applications](https://learn.microsoft.com/training/paths/get-started-c-sharp-part-6/) | [Debug and handle exceptions in a C# console application using Visual Studio Code](https://learn.microsoft.com/training/modules/guided-project-debug-handle-exceptions-c-sharp-console-application/), [Code]() | [Challenge - Debug a C# console application](https://learn.microsoft.com/training/modules/challenge-project-debug-c-sharp-console-application/), [Code]()
## Topics you'll learn
diff --git a/2-csharp/1-projects/challenge-project/ChallengeProject/Final/Final.csproj b/2-csharp/lesson-2-projects/challenge-project/ChallengeProject/Final/Final.csproj
similarity index 100%
rename from 2-csharp/1-projects/challenge-project/ChallengeProject/Final/Final.csproj
rename to 2-csharp/lesson-2-projects/challenge-project/ChallengeProject/Final/Final.csproj
diff --git a/2-csharp/1-projects/challenge-project/ChallengeProject/Final/Program.cs b/2-csharp/lesson-2-projects/challenge-project/ChallengeProject/Final/Program.cs
similarity index 100%
rename from 2-csharp/1-projects/challenge-project/ChallengeProject/Final/Program.cs
rename to 2-csharp/lesson-2-projects/challenge-project/ChallengeProject/Final/Program.cs
diff --git a/2-csharp/1-projects/challenge-project/ChallengeProject/Starter/Program.cs b/2-csharp/lesson-2-projects/challenge-project/ChallengeProject/Starter/Program.cs
similarity index 100%
rename from 2-csharp/1-projects/challenge-project/ChallengeProject/Starter/Program.cs
rename to 2-csharp/lesson-2-projects/challenge-project/ChallengeProject/Starter/Program.cs
diff --git a/2-csharp/1-projects/challenge-project/ChallengeProject/Starter/Starter.csproj b/2-csharp/lesson-2-projects/challenge-project/ChallengeProject/Starter/Starter.csproj
similarity index 100%
rename from 2-csharp/1-projects/challenge-project/ChallengeProject/Starter/Starter.csproj
rename to 2-csharp/lesson-2-projects/challenge-project/ChallengeProject/Starter/Starter.csproj
diff --git a/2-csharp/1-projects/challenge-project/LICENSE b/2-csharp/lesson-2-projects/challenge-project/LICENSE
similarity index 100%
rename from 2-csharp/1-projects/challenge-project/LICENSE
rename to 2-csharp/lesson-2-projects/challenge-project/LICENSE
diff --git a/2-csharp/1-projects/challenge-project/README.md b/2-csharp/lesson-2-projects/challenge-project/README.md
similarity index 100%
rename from 2-csharp/1-projects/challenge-project/README.md
rename to 2-csharp/lesson-2-projects/challenge-project/README.md
diff --git a/2-csharp/1-projects/guided-project/Final/Final.csproj b/2-csharp/lesson-2-projects/guided-project/Final/Final.csproj
similarity index 100%
rename from 2-csharp/1-projects/guided-project/Final/Final.csproj
rename to 2-csharp/lesson-2-projects/guided-project/Final/Final.csproj
diff --git a/2-csharp/1-projects/guided-project/Final/Program.cs b/2-csharp/lesson-2-projects/guided-project/Final/Program.cs
similarity index 100%
rename from 2-csharp/1-projects/guided-project/Final/Program.cs
rename to 2-csharp/lesson-2-projects/guided-project/Final/Program.cs
diff --git a/2-csharp/1-projects/guided-project/Starter/Program.cs b/2-csharp/lesson-2-projects/guided-project/Starter/Program.cs
similarity index 100%
rename from 2-csharp/1-projects/guided-project/Starter/Program.cs
rename to 2-csharp/lesson-2-projects/guided-project/Starter/Program.cs
diff --git a/2-csharp/1-projects/guided-project/Starter/Starter.csproj b/2-csharp/lesson-2-projects/guided-project/Starter/Starter.csproj
similarity index 100%
rename from 2-csharp/1-projects/guided-project/Starter/Starter.csproj
rename to 2-csharp/lesson-2-projects/guided-project/Starter/Starter.csproj
diff --git a/2-csharp/2-projects/projects/Final/Final.csproj b/2-csharp/lesson-3-projects/challenge-project/Final/Final.csproj
similarity index 100%
rename from 2-csharp/2-projects/projects/Final/Final.csproj
rename to 2-csharp/lesson-3-projects/challenge-project/Final/Final.csproj
diff --git a/2-csharp/lesson-3-projects/challenge-project/Final/Program.cs b/2-csharp/lesson-3-projects/challenge-project/Final/Program.cs
new file mode 100644
index 0000000..c4cb287
--- /dev/null
+++ b/2-csharp/lesson-3-projects/challenge-project/Final/Program.cs
@@ -0,0 +1,430 @@
+using System;
+using System.IO;
+
+// the ourAnimals array will store the following:
+string animalSpecies = "";
+string animalID = "";
+string animalAge = "";
+string animalPhysicalDescription = "";
+string animalPersonalityDescription = "";
+string animalNickname = "";
+
+// variables that support data entry
+int maxPets = 8;
+string? readResult;
+string menuSelection = "";
+int petCount = 0;
+string anotherPet = "y";
+bool validEntry = false;
+int petAge = 0;
+
+// array used to store runtime data, there is no persisted data
+string[,] ourAnimals = new string[maxPets, 6];
+
+// create some initial ourAnimals array entries
+for (int i = 0; i < maxPets; i++)
+{
+ switch (i)
+ {
+ case 0:
+ animalSpecies = "dog";
+ animalID = "d1";
+ animalAge = "2";
+ animalPhysicalDescription = "medium sized cream colored female golden retriever weighing about 65 pounds. housebroken.";
+ animalPersonalityDescription = "loves to have her belly rubbed and likes to chase her tail. gives lots of kisses.";
+ animalNickname = "lola";
+ break;
+
+ case 1:
+ animalSpecies = "dog";
+ animalID = "d2";
+ animalAge = "9";
+ animalPhysicalDescription = "large reddish-brown male golden retriever weighing about 85 pounds. housebroken.";
+ animalPersonalityDescription = "loves to have his ears rubbed when he greets you at the door, or at any time! loves to lean-in and give doggy hugs.";
+ animalNickname = "loki";
+ break;
+
+ case 2:
+ animalSpecies = "cat";
+ animalID = "c3";
+ animalAge = "1";
+ animalPhysicalDescription = "small white female weighing about 8 pounds. litter box trained.";
+ animalPersonalityDescription = "friendly";
+ animalNickname = "Puss";
+ break;
+
+ case 3:
+ animalSpecies = "cat";
+ animalID = "c4";
+ animalAge = "?";
+ animalPhysicalDescription = "";
+ animalPersonalityDescription = "";
+ animalNickname = "";
+
+ break;
+
+ default:
+ animalSpecies = "";
+ animalID = "";
+ animalAge = "";
+ animalPhysicalDescription = "";
+ animalPersonalityDescription = "";
+ animalNickname = "";
+ break;
+
+ }
+
+ ourAnimals[i, 0] = "ID #: " + animalID;
+ ourAnimals[i, 1] = "Species: " + animalSpecies;
+ ourAnimals[i, 2] = "Age: " + animalAge;
+ ourAnimals[i, 3] = "Nickname: " + animalNickname;
+ ourAnimals[i, 4] = "Physical description: " + animalPhysicalDescription;
+ ourAnimals[i, 5] = "Personality: " + animalPersonalityDescription;
+}
+
+// display the top-level menu options
+do
+{
+ Console.Clear();
+
+ Console.WriteLine("Welcome to the Contoso PetFriends app. Your main menu options are:");
+ Console.WriteLine(" 1. List all of our current pet information");
+ Console.WriteLine(" 2. Add a new animal friend to the ourAnimals array");
+ Console.WriteLine(" 3. Ensure animal ages and physical descriptions are complete");
+ Console.WriteLine(" 4. Ensure animal nicknames and personality descriptions are complete");
+ Console.WriteLine(" 5. Edit an animal’s age");
+ Console.WriteLine(" 6. Edit an animal’s personality description");
+ Console.WriteLine(" 7. Display all cats with a specified characteristic");
+ Console.WriteLine(" 8. Display all dogs with a specified characteristic");
+ Console.WriteLine();
+ Console.WriteLine("Enter your selection number (or type Exit to exit the program)");
+
+ readResult = Console.ReadLine();
+ if (readResult != null)
+ {
+ menuSelection = readResult.ToLower();
+ // NOTE: We could put a do statement around the menuSelection entry to ensure a valid entry, but we
+ // use a conditional statement below that only processes the valid entry values, so the do statement
+ // is not required here.
+ }
+
+ // use switch-case to process the selected menu option
+ switch (menuSelection)
+ {
+ case "1":
+ // List all of our current pet information
+ for (int i = 0; i < maxPets; i++)
+ {
+ if (ourAnimals[i, 0] != "ID #: ")
+ {
+ Console.WriteLine();
+ for (int j = 0; j < 6; j++)
+ {
+ Console.WriteLine(ourAnimals[i, j].ToString());
+ }
+ }
+ }
+ Console.WriteLine("\n\rPress the Enter key to continue");
+ readResult = Console.ReadLine();
+
+ break;
+
+ case "2":
+ // Add a new animal friend to the ourAnimals array
+ //
+ // The ourAnimals array contains
+ // 1. the species (cat or dog). a required field
+ // 2. the ID number - for example C17
+ // 3. the pet's age. can be blank at initial entry.
+ // 4. the pet's nickname. can be blank.
+ // 5. a description of the pet's physical appearance. can be blank.
+ // 6. a description of the pet's personality. can be blank.
+
+ anotherPet = "y";
+ petCount = 0;
+ for (int i = 0; i < maxPets; i++)
+ {
+ if (ourAnimals[i, 0] != "ID #: ")
+ {
+ petCount += 1;
+ }
+ }
+
+ if (petCount < maxPets)
+ {
+ Console.WriteLine($"We currently have {petCount} pets that need homes. We can manage {(maxPets - petCount)} more.");
+ }
+
+ while (anotherPet == "y" && petCount < maxPets)
+ {
+ // get species (cat or dog) - string animalSpecies is a required field
+ do
+ {
+ Console.WriteLine("\n\rEnter 'dog' or 'cat' to begin a new entry");
+ readResult = Console.ReadLine();
+ if (readResult != null)
+ {
+ animalSpecies = readResult.ToLower();
+ if (animalSpecies != "dog" && animalSpecies != "cat")
+ {
+ //Console.WriteLine($"You entered: {animalSpecies}.");
+ validEntry = false;
+ }
+ else
+ {
+ validEntry = true;
+ }
+ }
+ } while (validEntry == false);
+
+ // build the animal the ID number - for example C1, C2, D3 (for Cat 1, Cat 2, Dog 3)
+ animalID = animalSpecies.Substring(0, 1) + (petCount + 1).ToString();
+
+ // get the pet's age. can be ? at initial entry.
+ do
+ {
+ Console.WriteLine("Enter the pet's age or enter ? if unknown");
+ readResult = Console.ReadLine();
+ if (readResult != null)
+ {
+ animalAge = readResult;
+ if (animalAge != "?")
+ {
+ validEntry = int.TryParse(animalAge, out petAge);
+ }
+ }
+ } while (validEntry == false);
+
+
+ // get a description of the pet's physical appearance - animalPhysicalDescription can be blank.
+ do
+ {
+ Console.WriteLine("Enter a physical description of the pet (size, color, gender, weight, housebroken)");
+ readResult = Console.ReadLine();
+ if (readResult != null)
+ {
+ animalPhysicalDescription = readResult.ToLower();
+ if (animalPhysicalDescription == "")
+ {
+ animalPhysicalDescription = "tbd";
+ }
+ }
+ } while (validEntry == false);
+
+
+ // get a description of the pet's personality - animalPersonalityDescription can be blank.
+ do
+ {
+ Console.WriteLine("Enter a description of the pet's personality (likes or dislikes, tricks, energy level)");
+ readResult = Console.ReadLine();
+ if (readResult != null)
+ {
+ animalPersonalityDescription = readResult.ToLower();
+ if (animalPersonalityDescription == "")
+ {
+ animalPersonalityDescription = "tbd";
+ }
+ }
+ } while (validEntry == false);
+
+
+ // get the pet's nickname. animalNickname can be blank.
+ do
+ {
+ Console.WriteLine("Enter a nickname for the pet");
+ readResult = Console.ReadLine();
+ if (readResult != null)
+ {
+ animalNickname = readResult.ToLower();
+ if (animalNickname == "")
+ {
+ animalNickname = "tbd";
+ }
+ }
+ } while (validEntry == false);
+
+ // store the pet information in the ourAnimals array (zero based)
+ ourAnimals[petCount, 0] = "ID #: " + animalID;
+ ourAnimals[petCount, 1] = "Species: " + animalSpecies;
+ ourAnimals[petCount, 2] = "Age: " + animalAge;
+ ourAnimals[petCount, 3] = "Nickname: " + animalNickname;
+ ourAnimals[petCount, 4] = "Physical description: " + animalPhysicalDescription;
+ ourAnimals[petCount, 5] = "Personality: " + animalPersonalityDescription;
+
+ // increment petCount (the array is zero-based, so we increment the counter after adding to the array)
+ petCount = petCount + 1;
+
+ // check maxPet limit
+ if (petCount < maxPets)
+ {
+ // another pet?
+ Console.WriteLine("Do you want to enter info for another pet (y/n)");
+ do
+ {
+ readResult = Console.ReadLine();
+ if (readResult != null)
+ {
+ anotherPet = readResult.ToLower();
+ }
+
+ } while (anotherPet != "y" && anotherPet != "n");
+ }
+ //NOTE: The value of anotherPet (either "y" or "n") is evaluated in the while statement expression - at the top of the while loop
+ }
+
+ if (petCount >= maxPets)
+ {
+ Console.WriteLine("We have reached our limit on the number of pets that we can manage.");
+ Console.WriteLine("Press the Enter key to continue.");
+ readResult = Console.ReadLine();
+ }
+
+ break;
+
+ case "3":
+ // Ensure animal ages and physical descriptions are complete
+ //
+ // ourAnimals[i, 2] = "Age: " + animalAge;
+ // ourAnimals[i, 4] = "Physical description: " + animalPhysicalDescription;
+
+ for (int i = 0; i < maxPets; i++)
+ {
+ if (ourAnimals[i, 2] == "Age: ?" && ourAnimals[i, 0] != "ID #: ")
+ {
+ do
+ {
+ Console.WriteLine($"Enter an age for {ourAnimals[i, 0]}");
+ readResult = Console.ReadLine();
+ if (readResult != null)
+ {
+ animalAge = readResult;
+ validEntry = int.TryParse(animalAge, out petAge);
+ }
+ } while (validEntry == false);
+ ourAnimals[i, 2] = "Age: " + animalAge.ToString();
+ }
+
+ if (ourAnimals[i, 4] == "Physical description: " && ourAnimals[i, 0] != "ID #: ")
+ {
+ do
+ {
+ Console.WriteLine($"Enter a physical description for {ourAnimals[i, 0]} (size, color, gender, weight, housebroken)");
+ readResult = Console.ReadLine();
+ if (readResult != null)
+ {
+ animalPhysicalDescription = readResult.ToLower();
+ if (animalPhysicalDescription == "")
+ {
+ validEntry = false;
+ }
+ else
+ {
+ validEntry = true;
+ }
+
+ }
+ } while (validEntry == false);
+
+ ourAnimals[i, 4] = "Physical description: " + animalPhysicalDescription;
+ }
+ }
+ Console.WriteLine("\n\rAge and physical description fields are complete for all of our friends. \n\rPress the Enter key to continue");
+ readResult = Console.ReadLine();
+
+ break;
+
+ case "4":
+ // Ensure animal nickname and personality descriptions are complete
+ //
+ // ourAnimals[i, 3] = "Nickname: " + animalNickname;
+ // ourAnimals[i, 5] = "Personality: " + animalPersonalityDescription;
+
+ for (int i = 0; i < maxPets; i++)
+ {
+ if (ourAnimals[i, 3] == "Nickname: " && ourAnimals[i, 0] != "ID #: ")
+ {
+ do
+ {
+ Console.WriteLine($"Enter a nickname for {ourAnimals[i, 0]}");
+ readResult = Console.ReadLine();
+ if (readResult != null)
+ {
+ animalNickname = readResult;
+ if (animalNickname == "")
+ {
+ validEntry = false;
+ }
+ else
+ {
+ validEntry = true;
+ }
+
+ }
+
+ } while (validEntry == false);
+
+ ourAnimals[i, 3] = "Nickname: " + animalNickname;
+ }
+
+ if (ourAnimals[i, 5] == "Personality: " && ourAnimals[i, 0] != "ID #: ")
+ {
+ do
+ {
+ //"Enter a description of the pet's personality (likes or dislikes, tricks, energy level"
+ Console.WriteLine($"Enter a personality description for {ourAnimals[i, 0]} (likes or dislikes, tricks, energy level)");
+ readResult = Console.ReadLine();
+ if (readResult != null)
+ {
+ animalPersonalityDescription = readResult.ToLower();
+ if (animalPersonalityDescription == "")
+ {
+ validEntry = false;
+ }
+ else
+ {
+ validEntry = true;
+ }
+ }
+ } while (validEntry == false);
+
+ ourAnimals[i, 5] = "Personality: " + animalPersonalityDescription;
+ }
+ }
+ Console.WriteLine("\n\rAge and physical description fields are complete for all of our friends. \n\rPress the Enter key to continue");
+ readResult = Console.ReadLine();
+
+ break;
+
+ case "5":
+ // Edit an animal’s age");
+ Console.WriteLine("UNDER CONSTRUCTION - please check back next month to see progress.");
+ Console.WriteLine("Press the Enter key to continue.");
+ readResult = Console.ReadLine();
+ break;
+
+ case "6":
+ // Edit an animal’s personality description");
+ Console.WriteLine("UNDER CONSTRUCTION - please check back next month to see progress.");
+ Console.WriteLine("Press the Enter key to continue.");
+ readResult = Console.ReadLine();
+ break;
+
+ case "7":
+ // Display all cats with a specified characteristic
+ Console.WriteLine("UNDER CONSTRUCTION - please check back next month to see progress.");
+ Console.WriteLine("Press the Enter key to continue.");
+ readResult = Console.ReadLine();
+ break;
+
+ case "8":
+ // Display all dogs with a specified characteristic
+ Console.WriteLine("UNDER CONSTRUCTION - please check back next month to see progress.");
+ Console.WriteLine("Press the Enter key to continue.");
+ readResult = Console.ReadLine();
+ break;
+
+ default:
+ break;
+ }
+
+} while (menuSelection != "exit");
diff --git a/2-csharp/lesson-3-projects/challenge-project/Starter/Program.cs b/2-csharp/lesson-3-projects/challenge-project/Starter/Program.cs
new file mode 100644
index 0000000..647bf8a
--- /dev/null
+++ b/2-csharp/lesson-3-projects/challenge-project/Starter/Program.cs
@@ -0,0 +1,330 @@
+using System;
+using System.IO;
+
+// the ourAnimals array will store the following:
+string animalSpecies = "";
+string animalID = "";
+string animalAge = "";
+string animalPhysicalDescription = "";
+string animalPersonalityDescription = "";
+string animalNickname = "";
+
+// variables that support data entry
+int maxPets = 8;
+string? readResult;
+string menuSelection = "";
+int petCount = 0;
+string anotherPet = "y";
+bool validEntry = false;
+int petAge = 0;
+
+// array used to store runtime data, there is no persisted data
+string[,] ourAnimals = new string[maxPets, 6];
+
+// create some initial ourAnimals array entries
+for (int i = 0; i < maxPets; i++)
+{
+ switch (i)
+ {
+ case 0:
+ animalSpecies = "dog";
+ animalID = "d1";
+ animalAge = "2";
+ animalPhysicalDescription = "medium sized cream colored female golden retriever weighing about 65 pounds. housebroken.";
+ animalPersonalityDescription = "loves to have her belly rubbed and likes to chase her tail. gives lots of kisses.";
+ animalNickname = "lola";
+ break;
+
+ case 1:
+ animalSpecies = "dog";
+ animalID = "d2";
+ animalAge = "9";
+ animalPhysicalDescription = "large reddish-brown male golden retriever weighing about 85 pounds. housebroken.";
+ animalPersonalityDescription = "loves to have his ears rubbed when he greets you at the door, or at any time! loves to lean-in and give doggy hugs.";
+ animalNickname = "loki";
+ break;
+
+ case 2:
+ animalSpecies = "cat";
+ animalID = "c3";
+ animalAge = "1";
+ animalPhysicalDescription = "small white female weighing about 8 pounds. litter box trained.";
+ animalPersonalityDescription = "friendly";
+ animalNickname = "Puss";
+ break;
+
+ case 3:
+ animalSpecies = "cat";
+ animalID = "c4";
+ animalAge = "?";
+ animalPhysicalDescription = "";
+ animalPersonalityDescription = "";
+ animalNickname = "";
+
+ break;
+
+ default:
+ animalSpecies = "";
+ animalID = "";
+ animalAge = "";
+ animalPhysicalDescription = "";
+ animalPersonalityDescription = "";
+ animalNickname = "";
+ break;
+
+ }
+
+ ourAnimals[i, 0] = "ID #: " + animalID;
+ ourAnimals[i, 1] = "Species: " + animalSpecies;
+ ourAnimals[i, 2] = "Age: " + animalAge;
+ ourAnimals[i, 3] = "Nickname: " + animalNickname;
+ ourAnimals[i, 4] = "Physical description: " + animalPhysicalDescription;
+ ourAnimals[i, 5] = "Personality: " + animalPersonalityDescription;
+}
+
+// display the top-level menu options
+do
+{
+ Console.Clear();
+
+ Console.WriteLine("Welcome to the Contoso PetFriends app. Your main menu options are:");
+ Console.WriteLine(" 1. List all of our current pet information");
+ Console.WriteLine(" 2. Add a new animal friend to the ourAnimals array");
+ Console.WriteLine(" 3. Ensure animal ages and physical descriptions are complete");
+ Console.WriteLine(" 4. Ensure animal nicknames and personality descriptions are complete");
+ Console.WriteLine(" 5. Edit an animal’s age");
+ Console.WriteLine(" 6. Edit an animal’s personality description");
+ Console.WriteLine(" 7. Display all cats with a specified characteristic");
+ Console.WriteLine(" 8. Display all dogs with a specified characteristic");
+ Console.WriteLine();
+ Console.WriteLine("Enter your selection number (or type Exit to exit the program)");
+
+ readResult = Console.ReadLine();
+ if (readResult != null)
+ {
+ menuSelection = readResult.ToLower();
+ // NOTE: We could put a do statement around the menuSelection entry to ensure a valid entry, but we
+ // use a conditional statement below that only processes the valid entry values, so the do statement
+ // is not required here.
+ }
+
+ // use switch-case to process the selected menu option
+ switch (menuSelection)
+ {
+ case "1":
+ // List all of our current pet information
+ for (int i = 0; i < maxPets; i++)
+ {
+ if (ourAnimals[i, 0] != "ID #: ")
+ {
+ Console.WriteLine();
+ for (int j = 0; j < 6; j++)
+ {
+ Console.WriteLine(ourAnimals[i, j].ToString());
+ }
+ }
+ }
+ Console.WriteLine("\n\rPress the Enter key to continue");
+ readResult = Console.ReadLine();
+
+ break;
+
+ case "2":
+ // Add a new animal friend to the ourAnimals array
+ //
+ // The ourAnimals array contains
+ // 1. the species (cat or dog). a required field
+ // 2. the ID number - for example C17
+ // 3. the pet's age. can be blank at initial entry.
+ // 4. the pet's nickname. can be blank.
+ // 5. a description of the pet's physical appearance. can be blank.
+ // 6. a description of the pet's personality. can be blank.
+
+ anotherPet = "y";
+ petCount = 0;
+ for (int i = 0; i < maxPets; i++)
+ {
+ if (ourAnimals[i, 0] != "ID #: ")
+ {
+ petCount += 1;
+ }
+ }
+
+ if (petCount < maxPets)
+ {
+ Console.WriteLine($"We currently have {petCount} pets that need homes. We can manage {(maxPets - petCount)} more.");
+ }
+
+ while (anotherPet == "y" && petCount < maxPets)
+ {
+ // get species (cat or dog) - string animalSpecies is a required field
+ do
+ {
+ Console.WriteLine("\n\rEnter 'dog' or 'cat' to begin a new entry");
+ readResult = Console.ReadLine();
+ if (readResult != null)
+ {
+ animalSpecies = readResult.ToLower();
+ if (animalSpecies != "dog" && animalSpecies != "cat")
+ {
+ //Console.WriteLine($"You entered: {animalSpecies}.");
+ validEntry = false;
+ }
+ else
+ {
+ validEntry = true;
+ }
+ }
+ } while (validEntry == false);
+
+ // build the animal the ID number - for example C1, C2, D3 (for Cat 1, Cat 2, Dog 3)
+ animalID = animalSpecies.Substring(0, 1) + (petCount + 1).ToString();
+
+ // get the pet's age. can be ? at initial entry.
+ do
+ {
+ Console.WriteLine("Enter the pet's age or enter ? if unknown");
+ readResult = Console.ReadLine();
+ if (readResult != null)
+ {
+ animalAge = readResult;
+ if (animalAge != "?")
+ {
+ validEntry = int.TryParse(animalAge, out petAge);
+ }
+ }
+ } while (validEntry == false);
+
+
+ // get a description of the pet's physical appearance - animalPhysicalDescription can be blank.
+ do
+ {
+ Console.WriteLine("Enter a physical description of the pet (size, color, gender, weight, housebroken)");
+ readResult = Console.ReadLine();
+ if (readResult != null)
+ {
+ animalPhysicalDescription = readResult.ToLower();
+ if (animalPhysicalDescription == "")
+ {
+ animalPhysicalDescription = "tbd";
+ }
+ }
+ } while (validEntry == false);
+
+
+ // get a description of the pet's personality - animalPersonalityDescription can be blank.
+ do
+ {
+ Console.WriteLine("Enter a description of the pet's personality (likes or dislikes, tricks, energy level)");
+ readResult = Console.ReadLine();
+ if (readResult != null)
+ {
+ animalPersonalityDescription = readResult.ToLower();
+ if (animalPersonalityDescription == "")
+ {
+ animalPersonalityDescription = "tbd";
+ }
+ }
+ } while (validEntry == false);
+
+
+ // get the pet's nickname. animalNickname can be blank.
+ do
+ {
+ Console.WriteLine("Enter a nickname for the pet");
+ readResult = Console.ReadLine();
+ if (readResult != null)
+ {
+ animalNickname = readResult.ToLower();
+ if (animalNickname == "")
+ {
+ animalNickname = "tbd";
+ }
+ }
+ } while (validEntry == false);
+
+ // store the pet information in the ourAnimals array (zero based)
+ ourAnimals[petCount, 0] = "ID #: " + animalID;
+ ourAnimals[petCount, 1] = "Species: " + animalSpecies;
+ ourAnimals[petCount, 2] = "Age: " + animalAge;
+ ourAnimals[petCount, 3] = "Nickname: " + animalNickname;
+ ourAnimals[petCount, 4] = "Physical description: " + animalPhysicalDescription;
+ ourAnimals[petCount, 5] = "Personality: " + animalPersonalityDescription;
+
+ // increment petCount (the array is zero-based, so we increment the counter after adding to the array)
+ petCount = petCount + 1;
+
+ // check maxPet limit
+ if (petCount < maxPets)
+ {
+ // another pet?
+ Console.WriteLine("Do you want to enter info for another pet (y/n)");
+ do
+ {
+ readResult = Console.ReadLine();
+ if (readResult != null)
+ {
+ anotherPet = readResult.ToLower();
+ }
+
+ } while (anotherPet != "y" && anotherPet != "n");
+ }
+ //NOTE: The value of anotherPet (either "y" or "n") is evaluated in the while statement expression - at the top of the while loop
+ }
+
+ if (petCount >= maxPets)
+ {
+ Console.WriteLine("We have reached our limit on the number of pets that we can manage.");
+ Console.WriteLine("Press the Enter key to continue.");
+ readResult = Console.ReadLine();
+ }
+
+ break;
+
+ case "3":
+ // Ensure animal ages and physical descriptions are complete
+ Console.WriteLine("Challenge Project - please check back soon to see progress.");
+ Console.WriteLine("Press the Enter key to continue.");
+ readResult = Console.ReadLine();
+ break;
+
+ case "4":
+ // Ensure animal nicknames and personality descriptions are complete
+ Console.WriteLine("Challenge Project - please check back soon to see progress.");
+ Console.WriteLine("Press the Enter key to continue.");
+ readResult = Console.ReadLine();
+ break;
+
+ case "5":
+ // Edit an animal’s age");
+ Console.WriteLine("UNDER CONSTRUCTION - please check back next month to see progress.");
+ Console.WriteLine("Press the Enter key to continue.");
+ readResult = Console.ReadLine();
+ break;
+
+ case "6":
+ // Edit an animal’s personality description");
+ Console.WriteLine("UNDER CONSTRUCTION - please check back next month to see progress.");
+ Console.WriteLine("Press the Enter key to continue.");
+ readResult = Console.ReadLine();
+ break;
+
+ case "7":
+ // Display all cats with a specified characteristic
+ Console.WriteLine("UNDER CONSTRUCTION - please check back next month to see progress.");
+ Console.WriteLine("Press the Enter key to continue.");
+ readResult = Console.ReadLine();
+ break;
+
+ case "8":
+ // Display all dogs with a specified characteristic
+ Console.WriteLine("UNDER CONSTRUCTION - please check back next month to see progress.");
+ Console.WriteLine("Press the Enter key to continue.");
+ readResult = Console.ReadLine();
+ break;
+
+ default:
+ break;
+ }
+
+} while (menuSelection != "exit");
diff --git a/2-csharp/2-projects/projects/Starter/Starter.csproj b/2-csharp/lesson-3-projects/challenge-project/Starter/Starter.csproj
similarity index 100%
rename from 2-csharp/2-projects/projects/Starter/Starter.csproj
rename to 2-csharp/lesson-3-projects/challenge-project/Starter/Starter.csproj
diff --git a/2-csharp/lesson-3-projects/guided-project/Final/Final.csproj b/2-csharp/lesson-3-projects/guided-project/Final/Final.csproj
new file mode 100644
index 0000000..f02677b
--- /dev/null
+++ b/2-csharp/lesson-3-projects/guided-project/Final/Final.csproj
@@ -0,0 +1,10 @@
+
+
+
+ Exe
+ net7.0
+ enable
+ enable
+
+
+
diff --git a/2-csharp/2-projects/projects/Final/Program.cs b/2-csharp/lesson-3-projects/guided-project/Final/Program.cs
similarity index 100%
rename from 2-csharp/2-projects/projects/Final/Program.cs
rename to 2-csharp/lesson-3-projects/guided-project/Final/Program.cs
diff --git a/2-csharp/2-projects/projects/Starter/Program.cs b/2-csharp/lesson-3-projects/guided-project/Starter/Program.cs
similarity index 100%
rename from 2-csharp/2-projects/projects/Starter/Program.cs
rename to 2-csharp/lesson-3-projects/guided-project/Starter/Program.cs
diff --git a/2-csharp/lesson-3-projects/guided-project/Starter/Starter.csproj b/2-csharp/lesson-3-projects/guided-project/Starter/Starter.csproj
new file mode 100644
index 0000000..f02677b
--- /dev/null
+++ b/2-csharp/lesson-3-projects/guided-project/Starter/Starter.csproj
@@ -0,0 +1,10 @@
+
+
+
+ Exe
+ net7.0
+ enable
+ enable
+
+
+
diff --git a/2-csharp/lesson-4-projects/challenge-project/Final/Final.csproj b/2-csharp/lesson-4-projects/challenge-project/Final/Final.csproj
new file mode 100644
index 0000000..f02677b
--- /dev/null
+++ b/2-csharp/lesson-4-projects/challenge-project/Final/Final.csproj
@@ -0,0 +1,10 @@
+
+
+
+ Exe
+ net7.0
+ enable
+ enable
+
+
+
diff --git a/2-csharp/lesson-4-projects/challenge-project/Final/Program.cs b/2-csharp/lesson-4-projects/challenge-project/Final/Program.cs
new file mode 100644
index 0000000..bd2262e
--- /dev/null
+++ b/2-csharp/lesson-4-projects/challenge-project/Final/Program.cs
@@ -0,0 +1,228 @@
+// Final
+
+// ourAnimals array will store the following:
+string animalSpecies = "";
+string animalID = "";
+string animalAge = "";
+string animalPhysicalDescription = "";
+string animalPersonalityDescription = "";
+string animalNickname = "";
+string suggestedDonation = "";
+
+// variables that support data entry
+int maxPets = 8;
+string? readResult;
+string menuSelection = "";
+decimal decimalDonation = 0.00m;
+
+// array used to store runtime data
+string[,] ourAnimals = new string[maxPets, 7];
+
+// sample data ourAnimals array entries
+for (int i = 0; i < maxPets; i++)
+{
+ switch (i)
+ {
+ case 0:
+ animalSpecies = "dog";
+ animalID = "d1";
+ animalAge = "2";
+ animalPhysicalDescription = "medium sized cream colored female golden retriever weighing about 45 pounds. housebroken.";
+ animalPersonalityDescription = "loves to have her belly rubbed and likes to chase her tail. gives lots of kisses.";
+ animalNickname = "lola";
+ suggestedDonation = "85.00";
+ break;
+
+ case 1:
+ animalSpecies = "dog";
+ animalID = "d2";
+ animalAge = "9";
+ animalPhysicalDescription = "large reddish-brown male golden retriever weighing about 85 pounds. housebroken.";
+ animalPersonalityDescription = "loves to have his ears rubbed when he greets you at the door, or at any time! loves to lean-in and give doggy hugs.";
+ animalNickname = "gus";
+ suggestedDonation = "49.99";
+ break;
+
+ case 2:
+ animalSpecies = "cat";
+ animalID = "c3";
+ animalAge = "1";
+ animalPhysicalDescription = "small white female weighing about 8 pounds. litter box trained.";
+ animalPersonalityDescription = "friendly";
+ animalNickname = "snow";
+ suggestedDonation = "40.00";
+ break;
+
+ case 3:
+ animalSpecies = "cat";
+ animalID = "c4";
+ animalAge = "";
+ animalPhysicalDescription = "";
+ animalPersonalityDescription = "";
+ animalNickname = "lion";
+ suggestedDonation = "";
+
+ break;
+
+ default:
+ animalSpecies = "";
+ animalID = "";
+ animalAge = "";
+ animalPhysicalDescription = "";
+ animalPersonalityDescription = "";
+ animalNickname = "";
+ suggestedDonation = "";
+ break;
+ }
+
+ ourAnimals[i, 0] = "ID #: " + animalID;
+ ourAnimals[i, 1] = "Species: " + animalSpecies;
+ ourAnimals[i, 2] = "Age: " + animalAge;
+ ourAnimals[i, 3] = "Nickname: " + animalNickname;
+ ourAnimals[i, 4] = "Physical description: " + animalPhysicalDescription;
+ ourAnimals[i, 5] = "Personality: " + animalPersonalityDescription;
+
+ if (!decimal.TryParse(suggestedDonation, out decimalDonation))
+ {
+ decimalDonation = 45.00m; // if suggestedDonation NOT a number, default to 45.00
+ }
+ ourAnimals[i, 6] = $"Suggested Donation: {decimalDonation:C2}";
+}
+
+// top-level menu options
+do
+{
+ // NOTE: the Console.Clear method is throwing an exception in debug sessions
+ Console.Clear();
+
+ Console.WriteLine("Welcome to the Contoso PetFriends app. Your main menu options are:");
+ Console.WriteLine(" 1. List all of our current pet information");
+ Console.WriteLine(" 2. Display all dogs with a specified characteristic");
+ Console.WriteLine();
+ Console.WriteLine("Enter your selection number (or type Exit to exit the program)");
+
+ readResult = Console.ReadLine();
+
+ if (readResult != null)
+ {
+ menuSelection = readResult.ToLower();
+ }
+
+ // switch-case to process the selected menu option
+ switch (menuSelection)
+ {
+ case "1":
+ // list all pet info
+ for (int i = 0; i < maxPets; i++)
+ {
+ if (ourAnimals[i, 0] != "ID #: ")
+ {
+ Console.WriteLine();
+
+ for (int j = 0; j < 7; j++)
+ {
+ Console.WriteLine(ourAnimals[i, j].ToString());
+ }
+ }
+ }
+
+ Console.WriteLine("\r\nPress the Enter key to continue");
+ readResult = Console.ReadLine();
+
+ break;
+
+ case "2":
+ // #1 Display all dogs with a multiple search characteristics
+
+ string dogCharacteristics = "";
+
+ while (dogCharacteristics == "")
+ {
+ // #2 have user enter multiple comma separated characteristics to search for
+ Console.WriteLine($"\nEnter dog characteristics to search for separated by commas");
+ readResult = Console.ReadLine();
+
+ if (readResult != null)
+ {
+ dogCharacteristics = readResult.ToLower();
+ Console.WriteLine();
+ }
+ }
+
+ string[] dogSearches = dogCharacteristics.Split(",");
+ // trim leading and trailing spaces from each search term
+ for (int i = 0; i < dogSearches.Length; i++)
+ {
+ dogSearches[i] = dogSearches[i].Trim();
+ }
+
+ Array.Sort(dogSearches);
+ // #4 update to "rotating" animation with countdown
+ string[] searchingIcons = {" |", " /", "--", " \\", " *"};
+
+ bool matchesAnyDog = false;
+ string dogDescription = "";
+
+ // loops through the ourAnimals array to search for matching animals
+ for (int i = 0; i < maxPets; i++)
+ {
+ if (ourAnimals[i, 1].Contains("dog"))
+ {
+
+ // Search combined descriptions and report results
+ dogDescription = ourAnimals[i, 4] + "\n" + ourAnimals[i, 5];
+ bool matchesCurrentDog = false;
+
+ foreach (string term in dogSearches)
+ {
+ // only search if there is a term to search for
+ if (term != null && term.Trim() != "")
+ {
+ for (int j = 2; j > -1 ; j--)
+ {
+ // #5 update "searching" message to show countdown
+ foreach (string icon in searchingIcons)
+ {
+ Console.Write($"\rsearching our dog {ourAnimals[i, 3]} for {term.Trim()} {icon} {j.ToString()}");
+ Thread.Sleep(100);
+ }
+
+ Console.Write($"\r{new String(' ', Console.BufferWidth)}");
+ }
+
+ // #3a iterate submitted characteristic terms and search description for each term
+ if (dogDescription.Contains(" " + term.Trim() + " "))
+ {
+ // #3b update message to reflect current search term match
+
+ Console.WriteLine($"\rOur dog {ourAnimals[i, 3]} matches your search for {term.Trim()}");
+
+ matchesCurrentDog = true;
+ matchesAnyDog = true;
+ }
+ }
+ }
+
+ // #3d if the current dog is match, display the dog's info
+ if (matchesCurrentDog)
+ {
+ Console.WriteLine($"\r{ourAnimals[i, 3]} ({ourAnimals[i, 0]})\n{dogDescription}\n");
+ }
+ }
+ }
+
+ if (!matchesAnyDog)
+ {
+ Console.WriteLine("None of our dogs are a match found for: " + dogCharacteristics);
+ }
+
+ Console.WriteLine("\n\rPress the Enter key to continue");
+ readResult = Console.ReadLine();
+
+ break;
+
+ default:
+ break;
+ }
+}
+while (menuSelection != "exit");
diff --git a/2-csharp/lesson-4-projects/challenge-project/Starter/Program.cs b/2-csharp/lesson-4-projects/challenge-project/Starter/Program.cs
new file mode 100644
index 0000000..42d45bc
--- /dev/null
+++ b/2-csharp/lesson-4-projects/challenge-project/Starter/Program.cs
@@ -0,0 +1,206 @@
+using System;
+
+// ourAnimals array will store the following:
+string animalSpecies = "";
+string animalID = "";
+string animalAge = "";
+string animalPhysicalDescription = "";
+string animalPersonalityDescription = "";
+string animalNickname = "";
+string suggestedDonation = "";
+
+// variables that support data entry
+int maxPets = 8;
+string? readResult;
+string menuSelection = "";
+decimal decimalDonation = 0.00m;
+
+// array used to store runtime data
+string[,] ourAnimals = new string[maxPets, 7];
+
+// sample data ourAnimals array entries
+for (int i = 0; i < maxPets; i++)
+{
+ switch (i)
+ {
+ case 0:
+ animalSpecies = "dog";
+ animalID = "d1";
+ animalAge = "2";
+ animalPhysicalDescription = "medium sized cream colored female golden retriever weighing about 45 pounds. housebroken.";
+ animalPersonalityDescription = "loves to have her belly rubbed and likes to chase her tail. gives lots of kisses.";
+ animalNickname = "lola";
+ suggestedDonation = "85.00";
+ break;
+
+ case 1:
+ animalSpecies = "dog";
+ animalID = "d2";
+ animalAge = "9";
+ animalPhysicalDescription = "large reddish-brown male golden retriever weighing about 85 pounds. housebroken.";
+ animalPersonalityDescription = "loves to have his ears rubbed when he greets you at the door, or at any time! loves to lean-in and give doggy hugs.";
+ animalNickname = "gus";
+ suggestedDonation = "49.99";
+ break;
+
+ case 2:
+ animalSpecies = "cat";
+ animalID = "c3";
+ animalAge = "1";
+ animalPhysicalDescription = "small white female weighing about 8 pounds. litter box trained.";
+ animalPersonalityDescription = "friendly";
+ animalNickname = "snow";
+ suggestedDonation = "40.00";
+ break;
+
+ case 3:
+ animalSpecies = "cat";
+ animalID = "c4";
+ animalAge = "";
+ animalPhysicalDescription = "";
+ animalPersonalityDescription = "";
+ animalNickname = "lion";
+ suggestedDonation = "";
+
+ break;
+
+ default:
+ animalSpecies = "";
+ animalID = "";
+ animalAge = "";
+ animalPhysicalDescription = "";
+ animalPersonalityDescription = "";
+ animalNickname = "";
+ suggestedDonation = "";
+ break;
+
+ }
+
+ ourAnimals[i, 0] = "ID #: " + animalID;
+ ourAnimals[i, 1] = "Species: " + animalSpecies;
+ ourAnimals[i, 2] = "Age: " + animalAge;
+ ourAnimals[i, 3] = "Nickname: " + animalNickname;
+ ourAnimals[i, 4] = "Physical description: " + animalPhysicalDescription;
+ ourAnimals[i, 5] = "Personality: " + animalPersonalityDescription;
+
+ if (!decimal.TryParse(suggestedDonation, out decimalDonation)){
+ decimalDonation = 45.00m; // if suggestedDonation NOT a number, default to 45.00
+ }
+ ourAnimals[i, 6] = $"Suggested Donation: {decimalDonation:C2}";
+}
+
+// top-level menu options
+do
+{
+ // NOTE: the Console.Clear method is throwing an exception in debug sessions
+ Console.Clear();
+
+ Console.WriteLine("Welcome to the Contoso PetFriends app. Your main menu options are:");
+ Console.WriteLine(" 1. List all of our current pet information");
+ Console.WriteLine(" 2. Display all dogs with a specified characteristic");
+ Console.WriteLine();
+ Console.WriteLine("Enter your selection number (or type Exit to exit the program)");
+
+ readResult = Console.ReadLine();
+ if (readResult != null)
+ {
+ menuSelection = readResult.ToLower();
+ }
+
+ // switch-case to process the selected menu option
+ switch (menuSelection)
+ {
+ case "1":
+ // list all pet info
+ for (int i = 0; i < maxPets; i++)
+ {
+ if (ourAnimals[i, 0] != "ID #: ")
+ {
+ Console.WriteLine();
+ for (int j = 0; j < 7; j++)
+ {
+ Console.WriteLine(ourAnimals[i, j].ToString());
+ }
+ }
+ }
+
+ Console.WriteLine("\r\nPress the Enter key to continue");
+ readResult = Console.ReadLine();
+
+ break;
+
+ case "2":
+ // #1 Display all dogs with a multiple search characteristics
+
+ string dogCharacteristic = "";
+
+ while (dogCharacteristic == "")
+ {
+ // #2 have user enter multiple comma separated characteristics to search for
+ Console.WriteLine($"\r\nEnter one desired dog characteristic to search for");
+ readResult = Console.ReadLine();
+ if (readResult != null)
+ {
+ dogCharacteristic = readResult.ToLower().Trim();
+ Console.WriteLine();
+ }
+ }
+
+ bool noMatchesDog = true;
+ string dogDescription = "";
+
+ // #4 update to "rotating" animation with countdown
+ string[] searchingIcons = {". ", ".. ", "..."};
+
+ // loop ourAnimals array to search for matching animals
+ for (int i = 0; i < maxPets; i++)
+ {
+
+ if (ourAnimals[i, 1].Contains("dog"))
+ {
+
+ // Search combined descriptions and report results
+ dogDescription = ourAnimals[i, 4] + "\r\n" + ourAnimals[i, 5];
+
+ for (int j = 5; j > -1 ; j--)
+ {
+ // #5 update "searching" message to show countdown
+ foreach (string icon in searchingIcons)
+ {
+ Console.Write($"\rsearching our dog {ourAnimals[i, 3]} for {dogCharacteristic} {icon}");
+ Thread.Sleep(250);
+ }
+
+ Console.Write($"\r{new String(' ', Console.BufferWidth)}");
+ }
+
+ // #3a iterate submitted characteristic terms and search description for each term
+
+ if (dogDescription.Contains(dogCharacteristic))
+ {
+ // #3b update message to reflect term
+ // #3c set a flag "this dog" is a match
+ Console.WriteLine($"\nOur dog {ourAnimals[i, 3]} is a match!");
+
+ noMatchesDog = false;
+ }
+
+ // #3d if "this dog" is match write match message + dog description
+ }
+ }
+
+ if (noMatchesDog)
+ {
+ Console.WriteLine("None of our dogs are a match found for: " + dogCharacteristic);
+ }
+
+ Console.WriteLine("\n\rPress the Enter key to continue");
+ readResult = Console.ReadLine();
+
+ break;
+
+ default:
+ break;
+ }
+
+} while (menuSelection != "exit");
diff --git a/2-csharp/lesson-4-projects/challenge-project/Starter/Starter.csproj b/2-csharp/lesson-4-projects/challenge-project/Starter/Starter.csproj
new file mode 100644
index 0000000..f02677b
--- /dev/null
+++ b/2-csharp/lesson-4-projects/challenge-project/Starter/Starter.csproj
@@ -0,0 +1,10 @@
+
+
+
+ Exe
+ net7.0
+ enable
+ enable
+
+
+
diff --git a/2-csharp/lesson-4-projects/guided-project/Final/Final.csproj b/2-csharp/lesson-4-projects/guided-project/Final/Final.csproj
new file mode 100644
index 0000000..f02677b
--- /dev/null
+++ b/2-csharp/lesson-4-projects/guided-project/Final/Final.csproj
@@ -0,0 +1,10 @@
+
+
+
+ Exe
+ net7.0
+ enable
+ enable
+
+
+
diff --git a/2-csharp/lesson-4-projects/guided-project/Final/Program.cs b/2-csharp/lesson-4-projects/guided-project/Final/Program.cs
new file mode 100644
index 0000000..49dbc35
--- /dev/null
+++ b/2-csharp/lesson-4-projects/guided-project/Final/Program.cs
@@ -0,0 +1,189 @@
+// using System;
+
+// #1 the ourAnimals array will store the following:
+string animalSpecies = "";
+string animalID = "";
+string animalAge = "";
+string animalPhysicalDescription = "";
+string animalPersonalityDescription = "";
+string animalNickname = "";
+string suggestedDonation = "";
+
+// #2 variables that support data entry
+int maxPets = 8;
+string? readResult;
+string menuSelection = "";
+decimal decimalDonation = 0.00m;
+
+// #3 array used to store runtime data, there is no persisted data
+string[,] ourAnimals = new string[maxPets, 7];
+
+// #4 create sample data ourAnimals array entries
+for (int i = 0; i < maxPets; i++)
+{
+ switch (i)
+ {
+ case 0:
+ animalSpecies = "dog";
+ animalID = "d1";
+ animalAge = "2";
+ animalPhysicalDescription = "medium sized cream colored female golden retriever weighing about 45 pounds. housebroken.";
+ animalPersonalityDescription = "loves to have her belly rubbed and likes to chase her tail. gives lots of kisses.";
+ animalNickname = "lola";
+ suggestedDonation = "85.00";
+ break;
+
+ case 1:
+ animalSpecies = "dog";
+ animalID = "d2";
+ animalAge = "9";
+ animalPhysicalDescription = "large reddish-brown male golden retriever weighing about 85 pounds. housebroken.";
+ animalPersonalityDescription = "loves to have his ears rubbed when he greets you at the door, or at any time! loves to lean-in and give doggy hugs.";
+ animalNickname = "gus";
+ suggestedDonation = "49.99";
+ break;
+
+ case 2:
+ animalSpecies = "cat";
+ animalID = "c3";
+ animalAge = "1";
+ animalPhysicalDescription = "small white female weighing about 8 pounds. litter box trained.";
+ animalPersonalityDescription = "friendly";
+ animalNickname = "snow";
+ suggestedDonation = "40.00";
+ break;
+
+ case 3:
+ animalSpecies = "cat";
+ animalID = "c4";
+ animalAge = "";
+ animalPhysicalDescription = "";
+ animalPersonalityDescription = "";
+ animalNickname = "lion";
+ suggestedDonation = "";
+
+ break;
+
+ default:
+ animalSpecies = "";
+ animalID = "";
+ animalAge = "";
+ animalPhysicalDescription = "";
+ animalPersonalityDescription = "";
+ animalNickname = "";
+ suggestedDonation = "";
+ break;
+
+ }
+
+ ourAnimals[i, 0] = "ID #: " + animalID;
+ ourAnimals[i, 1] = "Species: " + animalSpecies;
+ ourAnimals[i, 2] = "Age: " + animalAge;
+ ourAnimals[i, 3] = "Nickname: " + animalNickname;
+ ourAnimals[i, 4] = "Physical description: " + animalPhysicalDescription;
+ ourAnimals[i, 5] = "Personality: " + animalPersonalityDescription;
+
+ if (!decimal.TryParse(suggestedDonation, out decimalDonation)){
+ decimalDonation = 45.00m; // if suggestedDonation NOT a number, default to 45.00
+ }
+ ourAnimals[i, 6] = $"Suggested Donation: {decimalDonation:C2}";
+}
+
+// #5 display the top-level menu options
+do
+{
+ // NOTE: the Console.Clear method is throwing an exception in debug sessions
+ Console.Clear();
+
+ Console.WriteLine("Welcome to the Contoso PetFriends app. Your main menu options are:");
+ Console.WriteLine(" 1. List all of our current pet information");
+ Console.WriteLine(" 2. Display all dogs with a specified characteristic");
+ Console.WriteLine();
+ Console.WriteLine("Enter your selection number (or type Exit to exit the program)");
+
+ readResult = Console.ReadLine();
+ if (readResult != null)
+ {
+ menuSelection = readResult.ToLower();
+ }
+
+ // use switch-case to process the selected menu option
+ switch (menuSelection)
+ {
+ case "1":
+ // list all pet info
+ for (int i = 0; i < maxPets; i++)
+ {
+ if (ourAnimals[i, 0] != "ID #: ")
+ {
+ Console.WriteLine();
+ for (int j = 0; j < 7; j++)
+ {
+ Console.WriteLine(ourAnimals[i, j].ToString());
+ }
+ }
+ }
+ Console.WriteLine("\n\rPress the Enter key to continue");
+ readResult = Console.ReadLine();
+
+ break;
+
+ case "2":
+ // Display all dogs with a specified characteristic");
+
+ string dogCharacteristic = "";
+
+ while (dogCharacteristic == "")
+ {
+ // have the user enter physical characteristics to search for
+ Console.WriteLine($"\nEnter one desired dog characteristics to search for");
+ readResult = Console.ReadLine();
+ if (readResult != null)
+ {
+ dogCharacteristic = readResult.ToLower().Trim();
+ }
+ }
+
+ bool noMatchesDog = true;
+ string dogDescription = "";
+
+ // #6 loop through the ourAnimals array to search for matching animals
+ for (int i = 0; i < maxPets; i++)
+ {
+ bool dogMatch = true;
+
+ if (ourAnimals[i, 1].Contains("dog"))
+ {
+
+ if (dogMatch == true)
+ {
+ // #7 Search combined descriptions and report results
+ dogDescription = ourAnimals[i, 4] + "\n" + ourAnimals[i, 5];
+
+
+ if (dogDescription.Contains(dogCharacteristic))
+ {
+ Console.WriteLine($"\nOur dog {ourAnimals[i, 3]} is a match!");
+ Console.WriteLine(dogDescription);
+
+ noMatchesDog = false;
+ }
+ }
+ }
+ }
+
+ if (noMatchesDog)
+ {
+ Console.WriteLine("None of our dogs are a match found for: " + dogCharacteristic);
+ }
+
+ Console.WriteLine("\n\rPress the Enter key to continue");
+ readResult = Console.ReadLine();
+
+ break;
+
+ default:
+ break;
+ }
+
+} while (menuSelection != "exit");
diff --git a/2-csharp/lesson-4-projects/guided-project/Starter/Program.cs b/2-csharp/lesson-4-projects/guided-project/Starter/Program.cs
new file mode 100644
index 0000000..ebdf12b
--- /dev/null
+++ b/2-csharp/lesson-4-projects/guided-project/Starter/Program.cs
@@ -0,0 +1,128 @@
+// #1 the ourAnimals array will store the following:
+string animalSpecies = "";
+string animalID = "";
+string animalAge = "";
+string animalPhysicalDescription = "";
+string animalPersonalityDescription = "";
+string animalNickname = "";
+
+// #2 variables that support data entry
+int maxPets = 8;
+string? readResult;
+string menuSelection = "";
+
+// #3 array used to store runtime data, there is no persisted data
+string[,] ourAnimals = new string[maxPets, 6];
+
+// #4 create sample data ourAnimals array entries
+for (int i = 0; i < maxPets; i++)
+{
+ switch (i)
+ {
+ case 0:
+ animalSpecies = "dog";
+ animalID = "d1";
+ animalAge = "2";
+ animalPhysicalDescription = "medium sized cream colored female golden retriever weighing about 45 pounds. housebroken.";
+ animalPersonalityDescription = "loves to have her belly rubbed and likes to chase her tail. gives lots of kisses.";
+ animalNickname = "lola";
+ break;
+
+ case 1:
+ animalSpecies = "dog";
+ animalID = "d2";
+ animalAge = "9";
+ animalPhysicalDescription = "large reddish-brown male golden retriever weighing about 85 pounds. housebroken.";
+ animalPersonalityDescription = "loves to have his ears rubbed when he greets you at the door, or at any time! loves to lean-in and give doggy hugs.";
+ animalNickname = "gus";
+ break;
+
+ case 2:
+ animalSpecies = "cat";
+ animalID = "c3";
+ animalAge = "1";
+ animalPhysicalDescription = "small white female weighing about 8 pounds. litter box trained.";
+ animalPersonalityDescription = "friendly";
+ animalNickname = "snow";
+ break;
+
+ case 3:
+ animalSpecies = "cat";
+ animalID = "c4";
+ animalAge = "3";
+ animalPhysicalDescription = "Medium sized, long hair, yellow, female, about 10 pounds. Uses litter box.";
+ animalPersonalityDescription = "A people loving cat that likes to sit on your lap.";
+ animalNickname = "Lion";
+ break;
+
+ default:
+ animalSpecies = "";
+ animalID = "";
+ animalAge = "";
+ animalPhysicalDescription = "";
+ animalPersonalityDescription = "";
+ animalNickname = "";
+ break;
+
+ }
+
+ ourAnimals[i, 0] = "ID #: " + animalID;
+ ourAnimals[i, 1] = "Species: " + animalSpecies;
+ ourAnimals[i, 2] = "Age: " + animalAge;
+ ourAnimals[i, 3] = "Nickname: " + animalNickname;
+ ourAnimals[i, 4] = "Physical description: " + animalPhysicalDescription;
+ ourAnimals[i, 5] = "Personality: " + animalPersonalityDescription;
+
+}
+
+// #5 display the top-level menu options
+do
+{
+ // NOTE: the Console.Clear method is throwing an exception in debug sessions
+ Console.Clear();
+
+ Console.WriteLine("Welcome to the Contoso PetFriends app. Your main menu options are:");
+ Console.WriteLine(" 1. List all of our current pet information");
+ Console.WriteLine(" 2. Display all dogs with a specified characteristic");
+ Console.WriteLine();
+ Console.WriteLine("Enter your selection number (or type Exit to exit the program)");
+
+ readResult = Console.ReadLine();
+ if (readResult != null)
+ {
+ menuSelection = readResult.ToLower();
+ }
+
+ // use switch-case to process the selected menu option
+ switch (menuSelection)
+ {
+ case "1":
+ // list all pet info
+ for (int i = 0; i < maxPets; i++)
+ {
+ if (ourAnimals[i, 0] != "ID #: ")
+ {
+ Console.WriteLine();
+ for (int j = 0; j < 6; j++)
+ {
+ Console.WriteLine(ourAnimals[i, j]);
+ }
+ }
+ }
+ Console.WriteLine("\n\rPress the Enter key to continue");
+ readResult = Console.ReadLine();
+
+ break;
+
+ case "2":
+ // Display all dogs with a specified characteristic
+ Console.WriteLine("\nUNDER CONSTRUCTION - please check back next month to see progress.");
+ Console.WriteLine("Press the Enter key to continue.");
+ readResult = Console.ReadLine();
+ break;
+
+ default:
+ break;
+ }
+
+} while (menuSelection != "exit");
diff --git a/2-csharp/lesson-4-projects/guided-project/Starter/Starter.csproj b/2-csharp/lesson-4-projects/guided-project/Starter/Starter.csproj
new file mode 100644
index 0000000..f02677b
--- /dev/null
+++ b/2-csharp/lesson-4-projects/guided-project/Starter/Starter.csproj
@@ -0,0 +1,10 @@
+
+
+
+ Exe
+ net7.0
+ enable
+ enable
+
+
+
diff --git a/2-csharp/lesson-5-projects/challenge-project/Final/Final.csproj b/2-csharp/lesson-5-projects/challenge-project/Final/Final.csproj
new file mode 100644
index 0000000..74abf5c
--- /dev/null
+++ b/2-csharp/lesson-5-projects/challenge-project/Final/Final.csproj
@@ -0,0 +1,10 @@
+
+
+
+ Exe
+ net6.0
+ enable
+ enable
+
+
+
diff --git a/2-csharp/lesson-5-projects/challenge-project/Final/Program.cs b/2-csharp/lesson-5-projects/challenge-project/Final/Program.cs
new file mode 100644
index 0000000..b4c9e74
--- /dev/null
+++ b/2-csharp/lesson-5-projects/challenge-project/Final/Program.cs
@@ -0,0 +1,162 @@
+using System;
+
+Random random = new Random();
+Console.CursorVisible = false;
+int height = Console.WindowHeight - 1;
+int width = Console.WindowWidth - 5;
+bool shouldExit = false;
+
+// Console position of the player
+int playerX = 0;
+int playerY = 0;
+
+// Console position of the food
+int foodX = 0;
+int foodY = 0;
+
+// Available player and food strings
+string[] states = {"('-')", "(^-^)", "(X_X)"};
+string[] foods = {"@@@@@", "$$$$$", "#####"};
+
+// Current player string displayed in the Console
+string player = states[0];
+
+// Index of the current food
+int food = 0;
+
+InitializeGame();
+while (!shouldExit)
+{
+ if (TerminalResized())
+ {
+ Console.Clear();
+ Console.Write("Console was resized. Program exiting.");
+ shouldExit = true;
+ }
+ else
+ {
+ if (PlayerIsFaster())
+ {
+ Move(1, false);
+ }
+ else if (PlayerIsSick())
+ {
+ FreezePlayer();
+ } else
+ {
+ Move(otherKeysExit: false);
+ }
+ if (GotFood())
+ {
+ ChangePlayer();
+ ShowFood();
+ }
+ }
+}
+
+// Returns true if the Terminal was resized
+bool TerminalResized()
+{
+ return height != Console.WindowHeight - 1 || width != Console.WindowWidth - 5;
+}
+
+// Displays random food at a random location
+void ShowFood()
+{
+ // Update food to a random index
+ food = random.Next(0, foods.Length);
+
+ // Update food position to a random location
+ foodX = random.Next(0, width - player.Length);
+ foodY = random.Next(0, height - 1);
+
+ // Display the food at the location
+ Console.SetCursorPosition(foodX, foodY);
+ Console.Write(foods[food]);
+}
+
+// Returns true if the player location matches the food location
+bool GotFood()
+{
+ return playerY == foodY && playerX == foodX;
+}
+
+// Returns true if the player appearance represents a sick state
+bool PlayerIsSick()
+{
+ return player.Equals(states[2]);
+}
+
+// Returns true if the player appearance represents a fast state
+bool PlayerIsFaster()
+{
+ return player.Equals(states[1]);
+}
+
+// Changes the player to match the food consumed
+void ChangePlayer()
+{
+ player = states[food];
+ Console.SetCursorPosition(playerX, playerY);
+ Console.Write(player);
+}
+
+// Temporarily stops the player from moving
+void FreezePlayer()
+{
+ System.Threading.Thread.Sleep(1000);
+ player = states[0];
+}
+
+// Reads directional input from the Console and moves the player
+void Move(int speed = 1, bool otherKeysExit = false)
+{
+ int lastX = playerX;
+ int lastY = playerY;
+
+ switch (Console.ReadKey(true).Key) {
+ case ConsoleKey.UpArrow:
+ playerY--;
+ break;
+ case ConsoleKey.DownArrow:
+ playerY++;
+ break;
+ case ConsoleKey.LeftArrow:
+ playerX -= speed;
+ break;
+ case ConsoleKey.RightArrow:
+ playerX += speed;
+ break;
+ case ConsoleKey.Escape:
+ shouldExit = true;
+ break;
+ default:
+ // Exit if any other keys are pressed
+ shouldExit = otherKeysExit;
+ break;
+ }
+
+ // Clear the characters at the previous position
+ Console.SetCursorPosition(lastX, lastY);
+ for (int i = 0; i < player.Length; i++)
+ {
+ Console.Write(" ");
+ }
+
+ // Keep player position within the bounds of the Terminal window
+ playerX = (playerX < 0) ? 0 : (playerX >= width ? width : playerX);
+ playerY = (playerY < 0) ? 0 : (playerY >= height ? height : playerY);
+
+ // Draw the player at the new location
+ Console.SetCursorPosition(playerX, playerY);
+ Console.Write(player);
+}
+
+// Clears the console, displays the food and player
+void InitializeGame()
+{
+ Console.Clear();
+ ShowFood();
+ Console.SetCursorPosition(0, 0);
+ Console.Write(player);
+}
\ No newline at end of file
diff --git a/2-csharp/lesson-5-projects/challenge-project/Starter/Program.cs b/2-csharp/lesson-5-projects/challenge-project/Starter/Program.cs
new file mode 100644
index 0000000..56bcd32
--- /dev/null
+++ b/2-csharp/lesson-5-projects/challenge-project/Starter/Program.cs
@@ -0,0 +1,117 @@
+using System;
+
+Random random = new Random();
+Console.CursorVisible = false;
+int height = Console.WindowHeight - 1;
+int width = Console.WindowWidth - 5;
+bool shouldExit = false;
+
+// Console position of the player
+int playerX = 0;
+int playerY = 0;
+
+// Console position of the food
+int foodX = 0;
+int foodY = 0;
+
+// Available player and food strings
+string[] states = {"('-')", "(^-^)", "(X_X)"};
+string[] foods = {"@@@@@", "$$$$$", "#####"};
+
+// Current player string displayed in the Console
+string player = states[0];
+
+// Index of the current food
+int food = 0;
+
+InitializeGame();
+while (!shouldExit)
+{
+ Move();
+}
+
+// Returns true if the Terminal was resized
+bool TerminalResized()
+{
+ return height != Console.WindowHeight - 1 || width != Console.WindowWidth - 5;
+}
+
+// Displays random food at a random location
+void ShowFood()
+{
+ // Update food to a random index
+ food = random.Next(0, foods.Length);
+
+ // Update food position to a random location
+ foodX = random.Next(0, width - player.Length);
+ foodY = random.Next(0, height - 1);
+
+ // Display the food at the location
+ Console.SetCursorPosition(foodX, foodY);
+ Console.Write(foods[food]);
+}
+
+// Changes the player to match the food consumed
+void ChangePlayer()
+{
+ player = states[food];
+ Console.SetCursorPosition(playerX, playerY);
+ Console.Write(player);
+}
+
+// Temporarily stops the player from moving
+void FreezePlayer()
+{
+ System.Threading.Thread.Sleep(1000);
+ player = states[0];
+}
+
+// Reads directional input from the Console and moves the player
+void Move()
+{
+ int lastX = playerX;
+ int lastY = playerY;
+
+ switch (Console.ReadKey(true).Key)
+ {
+ case ConsoleKey.UpArrow:
+ playerY--;
+ break;
+ case ConsoleKey.DownArrow:
+ playerY++;
+ break;
+ case ConsoleKey.LeftArrow:
+ playerX--;
+ break;
+ case ConsoleKey.RightArrow:
+ playerX++;
+ break;
+ case ConsoleKey.Escape:
+ shouldExit = true;
+ break;
+ }
+
+ // Clear the characters at the previous position
+ Console.SetCursorPosition(lastX, lastY);
+ for (int i = 0; i < player.Length; i++)
+ {
+ Console.Write(" ");
+ }
+
+ // Keep player position within the bounds of the Terminal window
+ playerX = (playerX < 0) ? 0 : (playerX >= width ? width : playerX);
+ playerY = (playerY < 0) ? 0 : (playerY >= height ? height : playerY);
+
+ // Draw the player at the new location
+ Console.SetCursorPosition(playerX, playerY);
+ Console.Write(player);
+}
+
+// Clears the console, displays the food and player
+void InitializeGame()
+{
+ Console.Clear();
+ ShowFood();
+ Console.SetCursorPosition(0, 0);
+ Console.Write(player);
+}
\ No newline at end of file
diff --git a/2-csharp/lesson-5-projects/challenge-project/Starter/Starter.csproj b/2-csharp/lesson-5-projects/challenge-project/Starter/Starter.csproj
new file mode 100644
index 0000000..74abf5c
--- /dev/null
+++ b/2-csharp/lesson-5-projects/challenge-project/Starter/Starter.csproj
@@ -0,0 +1,10 @@
+
+
+
+ Exe
+ net6.0
+ enable
+ enable
+
+
+
diff --git a/2-csharp/lesson-6-projects/challenge-project/Final/Final.csproj b/2-csharp/lesson-6-projects/challenge-project/Final/Final.csproj
new file mode 100644
index 0000000..f02677b
--- /dev/null
+++ b/2-csharp/lesson-6-projects/challenge-project/Final/Final.csproj
@@ -0,0 +1,10 @@
+
+
+
+ Exe
+ net7.0
+ enable
+ enable
+
+
+
diff --git a/2-csharp/lesson-6-projects/challenge-project/Final/Program.cs b/2-csharp/lesson-6-projects/challenge-project/Final/Program.cs
new file mode 100644
index 0000000..4db1da6
--- /dev/null
+++ b/2-csharp/lesson-6-projects/challenge-project/Final/Program.cs
@@ -0,0 +1,182 @@
+/*
+This application manages transactions at a store check-out line. The
+check-out line has a cash register, and the register has a cash till
+that is prepared with a number of bills each morning. The till includes
+bills of four denominations: $1, $5, $10, and $20. The till is used
+to provide the customer with change during the transaction. The item
+cost is a randomly generated number between 2 and 49. The customer
+offers payment based on an algorithm that determines a number of bills
+in each denomination.
+
+Each day, the cash till is loaded at the start of the day. As transactions
+occur, the cash till is managed in a method named MakeChange (customer
+payments go in and the change returned to the customer comes out). A
+separate "safety check" calculation that's used to verify the amount of
+money in the till is performed in the "main program". This safety check
+is used to ensure that logic in the MakeChange method is working as
+expected.
+*/
+
+string? readResult = null;
+bool useTestData = false;
+
+Console.Clear();
+
+int[] cashTill = new int[] { 0, 0, 0, 0 };
+int registerCheckTillTotal = 0;
+
+// registerDailyStartingCash: $1 x 50, $5 x 20, $10 x 10, $20 x 5 => ($350 total)
+int[,] registerDailyStartingCash = new int[,] { { 1, 50 }, { 5, 20 }, { 10, 10 }, { 20, 5 } };
+
+int[] testData = new int[] { 6, 10, 17, 20, 31, 36, 40, 41 };
+int testCounter = 0;
+
+LoadTillEachMorning(registerDailyStartingCash, cashTill);
+
+registerCheckTillTotal = registerDailyStartingCash[0, 0] * registerDailyStartingCash[0, 1] + registerDailyStartingCash[1, 0] * registerDailyStartingCash[1, 1] + registerDailyStartingCash[2, 0] * registerDailyStartingCash[2, 1] + registerDailyStartingCash[3, 0] * registerDailyStartingCash[3, 1];
+
+// display the number of bills of each denomination currently in the till
+LogTillStatus(cashTill);
+
+// display a message showing the amount of cash in the till
+Console.WriteLine(TillAmountSummary(cashTill));
+
+// display the expected registerDailyStartingCash total
+Console.WriteLine($"Expected till value: {registerCheckTillTotal}");
+Console.WriteLine();
+
+var valueGenerator = new Random((int)DateTime.Now.Ticks);
+
+int transactions = 100;
+
+if (useTestData)
+{
+ transactions = testData.Length;
+}
+
+while (transactions > 0)
+{
+ transactions -= 1;
+ int itemCost = valueGenerator.Next(2, 50);
+
+ if (useTestData)
+ {
+ itemCost = testData[testCounter];
+ testCounter += 1;
+ }
+
+ int paymentOnes = itemCost % 2; // value is 1 when itemCost is odd, value is 0 when itemCost is even
+ int paymentFives = (itemCost % 10 > 7) ? 1 : 0; // value is 1 when itemCost ends with 8 or 9, otherwise value is 0
+ int paymentTens = (itemCost % 20 > 13) ? 1 : 0; // value is 1 when 13 < itemCost < 20 OR 33 < itemCost < 40, otherwise value is 0
+ int paymentTwenties = (itemCost < 20) ? 1 : 2; // value is 1 when itemCost < 20, otherwise value is 2
+
+ // display messages describing the current transaction
+ Console.WriteLine($"Customer is making a ${itemCost} purchase");
+ Console.WriteLine($"\t Using {paymentTwenties} twenty dollar bills");
+ Console.WriteLine($"\t Using {paymentTens} ten dollar bills");
+ Console.WriteLine($"\t Using {paymentFives} five dollar bills");
+ Console.WriteLine($"\t Using {paymentOnes} one dollar bills");
+
+ try
+ {
+ // MakeChange manages the transaction and updates the till
+ MakeChange(itemCost, cashTill, paymentTwenties, paymentTens, paymentFives, paymentOnes);
+
+ // Backup Calculation - each transaction adds current "itemCost" to the till
+ registerCheckTillTotal += itemCost;
+ }
+ catch (InvalidOperationException e)
+ {
+ Console.WriteLine($"Could not complete transaction: {e.Message}");
+ }
+
+ Console.WriteLine(TillAmountSummary(cashTill));
+ Console.WriteLine($"Expected till value: {registerCheckTillTotal}");
+ Console.WriteLine();
+}
+
+Console.WriteLine("Press the Enter key to exit");
+do
+{
+ readResult = Console.ReadLine();
+
+} while (readResult == null);
+
+
+static void LoadTillEachMorning(int[,] registerDailyStartingCash, int[] cashTill)
+{
+ cashTill[0] = registerDailyStartingCash[0, 1];
+ cashTill[1] = registerDailyStartingCash[1, 1];
+ cashTill[2] = registerDailyStartingCash[2, 1];
+ cashTill[3] = registerDailyStartingCash[3, 1];
+}
+
+
+static void MakeChange(int cost, int[] cashTill, int twenties, int tens = 0, int fives = 0, int ones = 0)
+{
+ int availableTwenties = cashTill[3] + twenties;
+ int availableTens = cashTill[2] + tens;
+ int availableFives = cashTill[1] + fives;
+ int availableOnes = cashTill[0] + ones;
+
+ int amountPaid = twenties * 20 + tens * 10 + fives * 5 + ones;
+ int changeNeeded = amountPaid - cost;
+
+ if (changeNeeded < 0)
+ throw new InvalidOperationException("InvalidOperationException: Not enough money provided to complete the transaction.");
+
+ Console.WriteLine("Cashier prepares the following change:");
+
+ while ((changeNeeded > 19) && (availableTwenties > 0))
+ {
+ availableTwenties--;
+ changeNeeded -= 20;
+ Console.WriteLine("\t A twenty");
+ }
+
+ while ((changeNeeded > 9) && (availableTens > 0))
+ {
+ availableTens--;
+ changeNeeded -= 10;
+ Console.WriteLine("\t A ten");
+ }
+
+ while ((changeNeeded > 4) && (availableFives > 0))
+ {
+ availableFives--;
+ changeNeeded -= 5;
+ Console.WriteLine("\t A five");
+ }
+
+ while ((changeNeeded > 0) && (availableOnes > 0))
+ {
+ availableOnes--;
+ changeNeeded -= 1;
+ Console.WriteLine("\t A one");
+ }
+
+ if (changeNeeded > 0)
+ throw new InvalidOperationException("InvalidOperationException: The till is unable to make change for the cash provided.");
+
+ cashTill[0] = availableOnes;
+ cashTill[1] = availableFives;
+ cashTill[2] = availableTens;
+ cashTill[3] = availableTwenties;
+
+}
+
+static void LogTillStatus(int[] cashTill)
+{
+ Console.WriteLine("The till currently has:");
+ Console.WriteLine($"{cashTill[3] * 20} in twenties");
+ Console.WriteLine($"{cashTill[2] * 10} in tens");
+ Console.WriteLine($"{cashTill[1] * 5} in fives");
+ Console.WriteLine($"{cashTill[0]} in ones");
+ Console.WriteLine();
+}
+
+static string TillAmountSummary(int[] cashTill)
+{
+ return $"The till has {cashTill[3] * 20 + cashTill[2] * 10 + cashTill[1] * 5 + cashTill[0]} dollars";
+
+}
diff --git a/2-csharp/lesson-6-projects/challenge-project/Starter/Program.cs b/2-csharp/lesson-6-projects/challenge-project/Starter/Program.cs
new file mode 100644
index 0000000..b769206
--- /dev/null
+++ b/2-csharp/lesson-6-projects/challenge-project/Starter/Program.cs
@@ -0,0 +1,178 @@
+/*
+This application manages transactions at a store check-out line. The
+check-out line has a cash register, and the register has a cash till
+that is prepared with a number of bills each morning. The till includes
+bills of four denominations: $1, $5, $10, and $20. The till is used
+to provide the customer with change during the transaction. The item
+cost is a randomly generated number between 2 and 49. The customer
+offers payment based on an algorithm that determines a number of bills
+in each denomination.
+
+Each day, the cash till is loaded at the start of the day. As transactions
+occur, the cash till is managed in a method named MakeChange (customer
+payments go in and the change returned to the customer comes out). A
+separate "safety check" calculation that's used to verify the amount of
+money in the till is performed in the "main program". This safety check
+is used to ensure that logic in the MakeChange method is working as
+expected.
+*/
+
+
+string? readResult = null;
+bool useTestData = false;
+
+Console.Clear();
+
+int[] cashTill = new int[] { 0, 0, 0, 0 };
+int registerCheckTillTotal = 0;
+
+// registerDailyStartingCash: $1 x 50, $5 x 20, $10 x 10, $20 x 5 => ($350 total)
+int[,] registerDailyStartingCash = new int[,] { { 1, 50 }, { 5, 20 }, { 10, 10 }, { 20, 5 } };
+
+int[] testData = new int[] { 6, 10, 17, 20, 31, 36, 40, 41 };
+int testCounter = 0;
+
+LoadTillEachMorning(registerDailyStartingCash, cashTill);
+
+registerCheckTillTotal = registerDailyStartingCash[0, 0] * registerDailyStartingCash[0, 1] + registerDailyStartingCash[1, 0] * registerDailyStartingCash[1, 1] + registerDailyStartingCash[2, 0] * registerDailyStartingCash[2, 1] + registerDailyStartingCash[3, 0] * registerDailyStartingCash[3, 1];
+
+// display the number of bills of each denomination currently in the till
+LogTillStatus(cashTill);
+
+// display a message showing the amount of cash in the till
+Console.WriteLine(TillAmountSummary(cashTill));
+
+// display the expected registerDailyStartingCash total
+Console.WriteLine($"Expected till value: {registerCheckTillTotal}");
+Console.WriteLine();
+
+var valueGenerator = new Random((int)DateTime.Now.Ticks);
+
+int transactions = 100;
+
+if (useTestData)
+{
+ transactions = testData.Length;
+}
+
+while (transactions > 0)
+{
+ transactions -= 1;
+ int itemCost = valueGenerator.Next(2, 50);
+
+ if (useTestData)
+ {
+ itemCost = testData[testCounter];
+ testCounter += 1;
+ }
+
+ int paymentOnes = itemCost % 2; // value is 1 when itemCost is odd, value is 0 when itemCost is even
+ int paymentFives = (itemCost % 10 > 7) ? 1 : 0; // value is 1 when itemCost ends with 8 or 9, otherwise value is 0
+ int paymentTens = (itemCost % 20 > 13) ? 1 : 0; // value is 1 when 13 < itemCost < 20 OR 33 < itemCost < 40, otherwise value is 0
+ int paymentTwenties = (itemCost < 20) ? 1 : 2; // value is 1 when itemCost < 20, otherwise value is 2
+
+ // display messages describing the current transaction
+ Console.WriteLine($"Customer is making a ${itemCost} purchase");
+ Console.WriteLine($"\t Using {paymentTwenties} twenty dollar bills");
+ Console.WriteLine($"\t Using {paymentTens} ten dollar bills");
+ Console.WriteLine($"\t Using {paymentFives} five dollar bills");
+ Console.WriteLine($"\t Using {paymentOnes} one dollar bills");
+
+ try
+ {
+ // MakeChange manages the transaction and updates the till
+ MakeChange(itemCost, cashTill, paymentTwenties, paymentTens, paymentFives, paymentOnes);
+
+ // Backup Calculation - each transaction adds current "itemCost" to the till
+ registerCheckTillTotal += itemCost;
+ }
+ catch (InvalidOperationException e)
+ {
+ Console.WriteLine($"Could not complete transaction: {e.Message}");
+ }
+
+ Console.WriteLine(TillAmountSummary(cashTill));
+ Console.WriteLine($"Expected till value: {registerCheckTillTotal}");
+ Console.WriteLine();
+}
+
+Console.WriteLine("Press the Enter key to exit");
+do
+{
+ readResult = Console.ReadLine();
+
+} while (readResult == null);
+
+
+static void LoadTillEachMorning(int[,] registerDailyStartingCash, int[] cashTill)
+{
+ cashTill[0] = registerDailyStartingCash[0, 1];
+ cashTill[1] = registerDailyStartingCash[1, 1];
+ cashTill[2] = registerDailyStartingCash[2, 1];
+ cashTill[3] = registerDailyStartingCash[3, 1];
+}
+
+
+static void MakeChange(int cost, int[] cashTill, int twenties, int tens = 0, int fives = 0, int ones = 0)
+{
+ cashTill[3] += twenties;
+ cashTill[2] += tens;
+ cashTill[1] += fives;
+ cashTill[0] += ones;
+
+ int amountPaid = twenties * 20 + tens * 10 + fives * 5 + ones;
+ int changeNeeded = amountPaid - cost;
+
+ if (changeNeeded < 0)
+ throw new InvalidOperationException("InvalidOperationException: Not enough money provided to complete the transaction.");
+
+ Console.WriteLine("Cashier prepares the following change:");
+
+ while ((changeNeeded > 19) && (cashTill[3] > 0))
+ {
+ cashTill[3]--;
+ changeNeeded -= 20;
+ Console.WriteLine("\t A twenty");
+ }
+
+ while ((changeNeeded > 9) && (cashTill[2] > 0))
+ {
+ cashTill[2]--;
+ changeNeeded -= 10;
+ Console.WriteLine("\t A ten");
+ }
+
+ while ((changeNeeded > 4) && (cashTill[1] > 0))
+ {
+ cashTill[1]--;
+ changeNeeded -= 5;
+ Console.WriteLine("\t A five");
+ }
+
+ while ((changeNeeded > 0) && (cashTill[0] > 0))
+ {
+ cashTill[0]--;
+ changeNeeded -= 1;
+ Console.WriteLine("\t A one");
+ }
+
+ if (changeNeeded > 0)
+ throw new InvalidOperationException("InvalidOperationException: The till is unable to make change for the cash provided.");
+
+}
+
+static void LogTillStatus(int[] cashTill)
+{
+ Console.WriteLine("The till currently has:");
+ Console.WriteLine($"{cashTill[3] * 20} in twenties");
+ Console.WriteLine($"{cashTill[2] * 10} in tens");
+ Console.WriteLine($"{cashTill[1] * 5} in fives");
+ Console.WriteLine($"{cashTill[0]} in ones");
+ Console.WriteLine();
+}
+
+static string TillAmountSummary(int[] cashTill)
+{
+ return $"The till has {cashTill[3] * 20 + cashTill[2] * 10 + cashTill[1] * 5 + cashTill[0]} dollars";
+
+}
diff --git a/2-csharp/lesson-6-projects/challenge-project/Starter/Starter.csproj b/2-csharp/lesson-6-projects/challenge-project/Starter/Starter.csproj
new file mode 100644
index 0000000..f02677b
--- /dev/null
+++ b/2-csharp/lesson-6-projects/challenge-project/Starter/Starter.csproj
@@ -0,0 +1,10 @@
+
+
+
+ Exe
+ net7.0
+ enable
+ enable
+
+
+
diff --git a/2-csharp/lesson-6-projects/guided-project/Final/Final.csproj b/2-csharp/lesson-6-projects/guided-project/Final/Final.csproj
new file mode 100644
index 0000000..f02677b
--- /dev/null
+++ b/2-csharp/lesson-6-projects/guided-project/Final/Final.csproj
@@ -0,0 +1,10 @@
+
+
+
+ Exe
+ net7.0
+ enable
+ enable
+
+
+
diff --git a/2-csharp/lesson-6-projects/guided-project/Final/Program.cs b/2-csharp/lesson-6-projects/guided-project/Final/Program.cs
new file mode 100644
index 0000000..f50f7bc
--- /dev/null
+++ b/2-csharp/lesson-6-projects/guided-project/Final/Program.cs
@@ -0,0 +1,178 @@
+/*
+This application manages transactions at a store check-out line. The
+check-out line has a cash register, and the register has a cash till
+that is prepared with a number of bills each morning. The till includes
+bills of four denominations: $1, $5, $10, and $20. The till is used
+to provide the customer with change during the transaction. The item
+cost is a randomly generated number between 2 and 49. The customer
+offers payment based on an algorithm that determines a number of bills
+in each denomination.
+
+Each day, the cash till is loaded at the start of the day. As transactions
+occur, the cash till is managed in a method named MakeChange (customer
+payments go in and the change returned to the customer comes out). A
+separate "safety check" calculation that's used to verify the amount of
+money in the till is performed in the "main program". This safety check
+is used to ensure that logic in the MakeChange method is working as
+expected.
+*/
+
+
+string? readResult = null;
+bool useTestData = false;
+
+Console.Clear();
+
+int[] cashTill = new int[] { 0, 0, 0, 0 };
+int registerCheckTillTotal = 0;
+
+// registerDailyStartingCash: $1 x 50, $5 x 20, $10 x 10, $20 x 5 => ($350 total)
+int[,] registerDailyStartingCash = new int[,] { { 1, 50 }, { 5, 20 }, { 10, 10 }, { 20, 5 } };
+
+int[] testData = new int[] { 6, 10, 17, 20, 31, 36, 40, 41 };
+int testCounter = 0;
+
+LoadTillEachMorning(registerDailyStartingCash, cashTill);
+
+registerCheckTillTotal = registerDailyStartingCash[0, 0] * registerDailyStartingCash[0, 1] + registerDailyStartingCash[1, 0] * registerDailyStartingCash[1, 1] + registerDailyStartingCash[2, 0] * registerDailyStartingCash[2, 1] + registerDailyStartingCash[3, 0] * registerDailyStartingCash[3, 1];
+
+// display the number of bills of each denomination currently in the till
+LogTillStatus(cashTill);
+
+// display a message showing the amount of cash in the till
+Console.WriteLine(TillAmountSummary(cashTill));
+
+// display the expected registerDailyStartingCash total
+Console.WriteLine($"Expected till value: {registerCheckTillTotal}");
+Console.WriteLine();
+
+var valueGenerator = new Random((int)DateTime.Now.Ticks);
+
+int transactions = 10;
+
+if (useTestData)
+{
+ transactions = testData.Length;
+}
+
+while (transactions > 0)
+{
+ transactions -= 1;
+ int itemCost = valueGenerator.Next(2, 50);
+
+ if (useTestData)
+ {
+ itemCost = testData[testCounter];
+ testCounter += 1;
+ }
+
+ int paymentOnes = itemCost % 2; // value is 1 when itemCost is odd, value is 0 when itemCost is even
+ int paymentFives = (itemCost % 10 > 7) ? 1 : 0; // value is 1 when itemCost ends with 8 or 9, otherwise value is 0
+ int paymentTens = (itemCost % 20 > 13) ? 1 : 0; // value is 1 when 13 < itemCost < 20 OR 33 < itemCost < 40, otherwise value is 0
+ int paymentTwenties = (itemCost < 20) ? 1 : 2; // value is 1 when itemCost < 20, otherwise value is 2
+
+ // display messages describing the current transaction
+ Console.WriteLine($"Customer is making a ${itemCost} purchase");
+ Console.WriteLine($"\t Using {paymentTwenties} twenty dollar bills");
+ Console.WriteLine($"\t Using {paymentTens} ten dollar bills");
+ Console.WriteLine($"\t Using {paymentFives} five dollar bills");
+ Console.WriteLine($"\t Using {paymentOnes} one dollar bills");
+
+ try
+ {
+ // MakeChange manages the transaction and updates the till
+ MakeChange(itemCost, cashTill, paymentTwenties, paymentTens, paymentFives, paymentOnes);
+
+ // Backup Calculation - each transaction adds current "itemCost" to the till
+ registerCheckTillTotal += itemCost;
+ }
+ catch (InvalidOperationException e)
+ {
+ Console.WriteLine($"Could not make transaction: {e.Message}");
+ }
+
+ Console.WriteLine(TillAmountSummary(cashTill));
+ Console.WriteLine($"Expected till value: {registerCheckTillTotal}");
+ Console.WriteLine();
+}
+
+Console.WriteLine("Press the Enter key to exit");
+do
+{
+ readResult = Console.ReadLine();
+
+} while (readResult == null);
+
+
+static void LoadTillEachMorning(int[,] registerDailyStartingCash, int[] cashTill)
+{
+ cashTill[0] = registerDailyStartingCash[0, 1];
+ cashTill[1] = registerDailyStartingCash[1, 1];
+ cashTill[2] = registerDailyStartingCash[2, 1];
+ cashTill[3] = registerDailyStartingCash[3, 1];
+}
+
+
+static void MakeChange(int cost, int[] cashTill, int twenties, int tens = 0, int fives = 0, int ones = 0)
+{
+ cashTill[3] += twenties;
+ cashTill[2] += tens;
+ cashTill[1] += fives;
+ cashTill[0] += ones;
+
+ int amountPaid = twenties * 20 + tens * 10 + fives * 5 + ones;
+ int changeNeeded = amountPaid - cost;
+
+ if (changeNeeded < 0)
+ throw new InvalidOperationException("Not enough money provided");
+
+ Console.WriteLine("Cashier Returns:");
+
+ while ((changeNeeded > 19) && (cashTill[3] > 0))
+ {
+ cashTill[3]--;
+ changeNeeded -= 20;
+ Console.WriteLine("\t A twenty");
+ }
+
+ while ((changeNeeded > 9) && (cashTill[2] > 0))
+ {
+ cashTill[2]--;
+ changeNeeded -= 10;
+ Console.WriteLine("\t A ten");
+ }
+
+ while ((changeNeeded > 4) && (cashTill[1] > 0))
+ {
+ cashTill[1]--;
+ changeNeeded -= 5;
+ Console.WriteLine("\t A five");
+ }
+
+ while ((changeNeeded > 0) && (cashTill[0] > 0))
+ {
+ cashTill[0]--;
+ changeNeeded -= 1;
+ Console.WriteLine("\t A one");
+ }
+
+ if (changeNeeded > 0)
+ throw new InvalidOperationException("Can't make change. Do you have anything smaller?");
+
+}
+
+static void LogTillStatus(int[] cashTill)
+{
+ Console.WriteLine("The till currently has:");
+ Console.WriteLine($"{cashTill[3] * 20} in twenties");
+ Console.WriteLine($"{cashTill[2] * 10} in tens");
+ Console.WriteLine($"{cashTill[1] * 5} in fives");
+ Console.WriteLine($"{cashTill[0]} in ones");
+ Console.WriteLine();
+}
+
+static string TillAmountSummary(int[] cashTill)
+{
+ return $"The till has {cashTill[3] * 20 + cashTill[2] * 10 + cashTill[1] * 5 + cashTill[0]} dollars";
+
+}
diff --git a/2-csharp/lesson-6-projects/guided-project/Starter/Program.cs b/2-csharp/lesson-6-projects/guided-project/Starter/Program.cs
new file mode 100644
index 0000000..9cc76e1
--- /dev/null
+++ b/2-csharp/lesson-6-projects/guided-project/Starter/Program.cs
@@ -0,0 +1,183 @@
+/*
+This application manages transactions at a store check-out line. The
+check-out line has a cash register, and the register has a cash till
+that is prepared with a number of bills each morning. The till includes
+bills of four denominations: $1, $5, $10, and $20. The till is used
+to provide the customer with change during the transaction. The item
+cost is a randomly generated number between 2 and 49. The customer
+offers payment based on an algorithm that determines a number of bills
+in each denomination.
+
+Each day, the cash till is loaded at the start of the day. As transactions
+occur, the cash till is managed in a method named MakeChange (customer
+payments go in and the change returned to the customer comes out). A
+separate "safety check" calculation that's used to verify the amount of
+money in the till is performed in the "main program". This safety check
+is used to ensure that logic in the MakeChange method is working as
+expected.
+*/
+
+string? readResult = null;
+bool useTestData = true;
+
+Console.Clear();
+
+int[] cashTill = new int[] { 0, 0, 0, 0 };
+int registerCheckTillTotal = 0;
+
+// registerDailyStartingCash: $1 x 50, $5 x 20, $10 x 10, $20 x 5 => ($350 total)
+int[,] registerDailyStartingCash = new int[,] { { 1, 50 }, { 5, 20 }, { 10, 10 }, { 20, 5 } };
+
+int[] testData = new int[] { 6, 10, 17, 20, 31, 36, 40, 41 };
+int testCounter = 0;
+
+LoadTillEachMorning(registerDailyStartingCash, cashTill);
+
+registerCheckTillTotal = registerDailyStartingCash[0, 0] * registerDailyStartingCash[0, 1] + registerDailyStartingCash[1, 0] * registerDailyStartingCash[1, 1] + registerDailyStartingCash[2, 0] * registerDailyStartingCash[2, 1] + registerDailyStartingCash[3, 0] * registerDailyStartingCash[3, 1];
+
+// display the number of bills of each denomination currently in the till
+LogTillStatus(cashTill);
+
+// display a message showing the amount of cash in the till
+Console.WriteLine(TillAmountSummary(cashTill));
+
+// display the expected registerDailyStartingCash total
+Console.WriteLine($"Expected till value: {registerCheckTillTotal}\n\r");
+
+var valueGenerator = new Random((int)DateTime.Now.Ticks);
+
+int transactions = 10;
+
+if (useTestData)
+{
+ transactions = testData.Length;
+}
+
+while (transactions > 0)
+{
+ transactions -= 1;
+ int itemCost = valueGenerator.Next(2, 20);
+
+ if (useTestData)
+ {
+ itemCost = testData[testCounter];
+ testCounter += 1;
+ }
+
+ int paymentOnes = itemCost % 2; // value is 1 when itemCost is odd, value is 0 when itemCost is even
+ int paymentFives = (itemCost % 10 > 7) ? 1 : 0; // value is 1 when itemCost ends with 8 or 9, otherwise value is 0
+ int paymentTens = (itemCost % 20 > 13) ? 1 : 0; // value is 1 when 13 < itemCost < 20 OR 33 < itemCost < 40, otherwise value is 0
+ int paymentTwenties = (itemCost < 20) ? 1 : 2; // value is 1 when itemCost < 20, otherwise value is 2
+
+ // display messages describing the current transaction
+ Console.WriteLine($"Customer is making a ${itemCost} purchase");
+ Console.WriteLine($"\t Using {paymentTwenties} twenty dollar bills");
+ Console.WriteLine($"\t Using {paymentTens} ten dollar bills");
+ Console.WriteLine($"\t Using {paymentFives} five dollar bills");
+ Console.WriteLine($"\t Using {paymentOnes} one dollar bills");
+
+ // MakeChange manages the transaction and updates the till
+ string transactionMessage = MakeChange(itemCost, cashTill, paymentTwenties, paymentTens, paymentFives, paymentOnes);
+
+ // Backup Calculation - each transaction adds current "itemCost" to the till
+ if (transactionMessage == "transaction succeeded")
+ {
+ Console.WriteLine($"Transaction successfully completed.");
+ registerCheckTillTotal += itemCost;
+ }
+ else
+ {
+ Console.WriteLine($"Transaction unsuccessful: {transactionMessage}");
+ }
+
+ Console.WriteLine(TillAmountSummary(cashTill));
+ Console.WriteLine($"Expected till value: {registerCheckTillTotal}\n\r");
+ Console.WriteLine();
+}
+
+Console.WriteLine("Press the Enter key to exit");
+do
+{
+ readResult = Console.ReadLine();
+
+} while (readResult == null);
+
+
+static void LoadTillEachMorning(int[,] registerDailyStartingCash, int[] cashTill)
+{
+ cashTill[0] = registerDailyStartingCash[0, 1];
+ cashTill[1] = registerDailyStartingCash[1, 1];
+ cashTill[2] = registerDailyStartingCash[2, 1];
+ cashTill[3] = registerDailyStartingCash[3, 1];
+}
+
+
+static string MakeChange(int cost, int[] cashTill, int twenties, int tens = 0, int fives = 0, int ones = 0)
+{
+ string transactionMessage = "";
+
+ cashTill[3] += twenties;
+ cashTill[2] += tens;
+ cashTill[1] += fives;
+ cashTill[0] += ones;
+
+ int amountPaid = twenties * 20 + tens * 10 + fives * 5 + ones;
+ int changeNeeded = amountPaid - cost;
+
+ if (changeNeeded < 0)
+ transactionMessage = "Not enough money provided.";
+
+ Console.WriteLine("Cashier Returns:");
+
+ while ((changeNeeded > 19) && (cashTill[3] > 0))
+ {
+ cashTill[3]--;
+ changeNeeded -= 20;
+ Console.WriteLine("\t A twenty");
+ }
+
+ while ((changeNeeded > 9) && (cashTill[2] > 0))
+ {
+ cashTill[2]--;
+ changeNeeded -= 10;
+ Console.WriteLine("\t A ten");
+ }
+
+ while ((changeNeeded > 4) && (cashTill[1] > 0))
+ {
+ cashTill[2]--;
+ changeNeeded -= 5;
+ Console.WriteLine("\t A five");
+ }
+
+ while ((changeNeeded > 0) && (cashTill[0] > 0))
+ {
+ cashTill[0]--;
+ changeNeeded--;
+ Console.WriteLine("\t A one");
+ }
+
+ if (changeNeeded > 0)
+ transactionMessage = "Can't make change. Do you have anything smaller?";
+
+ if (transactionMessage == "")
+ transactionMessage = "transaction succeeded";
+
+ return transactionMessage;
+}
+
+static void LogTillStatus(int[] cashTill)
+{
+ Console.WriteLine("The till currently has:");
+ Console.WriteLine($"{cashTill[3] * 20} in twenties");
+ Console.WriteLine($"{cashTill[2] * 10} in tens");
+ Console.WriteLine($"{cashTill[1] * 5} in fives");
+ Console.WriteLine($"{cashTill[0]} in ones");
+ Console.WriteLine();
+}
+
+static string TillAmountSummary(int[] cashTill)
+{
+ return $"The till has {cashTill[3] * 20 + cashTill[2] * 10 + cashTill[1] * 5 + cashTill[0]} dollars";
+
+}
diff --git a/2-csharp/lesson-6-projects/guided-project/Starter/Starter.csproj b/2-csharp/lesson-6-projects/guided-project/Starter/Starter.csproj
new file mode 100644
index 0000000..f02677b
--- /dev/null
+++ b/2-csharp/lesson-6-projects/guided-project/Starter/Starter.csproj
@@ -0,0 +1,10 @@
+
+
+
+ Exe
+ net7.0
+ enable
+ enable
+
+
+