From 1a4efb427e2ee38a85933ad12e50f9a9fd88b8d2 Mon Sep 17 00:00:00 2001 From: Vladimir Pecanac Date: Sun, 8 Nov 2026 14:46:59 +0100 Subject: [PATCH] Stack in C#: move sample to .NET 10, fix nullable warnings, add empty-stack and ConcurrentStack demos and tests --- .../StackInCSharp/GenericStackHelper.cs | 8 +++-- .../StackInCSharp/NonGenericStackHelper.cs | 4 +-- .../StackInCSharp/StackInCSharp/Program.cs | 35 ++++++++++++++++--- .../StackInCSharp/StackInCSharp.csproj | 2 +- .../Tests/StackInCSharpUnitTests.cs | 24 +++++++++++++ .../StackInCSharp/Tests/Tests.csproj | 10 +++--- 6 files changed, 68 insertions(+), 15 deletions(-) diff --git a/collections-csharp/StackInCSharp/StackInCSharp/GenericStackHelper.cs b/collections-csharp/StackInCSharp/StackInCSharp/GenericStackHelper.cs index 4b8e528a1e..66297a275e 100644 --- a/collections-csharp/StackInCSharp/StackInCSharp/GenericStackHelper.cs +++ b/collections-csharp/StackInCSharp/StackInCSharp/GenericStackHelper.cs @@ -1,4 +1,6 @@ -namespace StackInCSharp; +using System.Diagnostics.CodeAnalysis; + +namespace StackInCSharp; public class GenericStackHelper { @@ -48,7 +50,7 @@ public T PopItem() return GenericStack.Pop(); } - public bool TryPeekItem(out T result) + public bool TryPeekItem([MaybeNullWhen(false)] out T result) { if (GenericStack == null) { @@ -58,7 +60,7 @@ public bool TryPeekItem(out T result) return GenericStack.TryPeek(out result); } - public bool TryPopItem(out T result) + public bool TryPopItem([MaybeNullWhen(false)] out T result) { if (GenericStack == null) { diff --git a/collections-csharp/StackInCSharp/StackInCSharp/NonGenericStackHelper.cs b/collections-csharp/StackInCSharp/StackInCSharp/NonGenericStackHelper.cs index 3f773f7d84..6469963885 100644 --- a/collections-csharp/StackInCSharp/StackInCSharp/NonGenericStackHelper.cs +++ b/collections-csharp/StackInCSharp/StackInCSharp/NonGenericStackHelper.cs @@ -31,7 +31,7 @@ public void PushItem(object o) NonGenericStack.Push(o); } - public object PeekItem() + public object? PeekItem() { if (NonGenericStack == null) { @@ -41,7 +41,7 @@ public object PeekItem() return NonGenericStack.Peek(); } - public object PopItem() + public object? PopItem() { if (NonGenericStack == null) { diff --git a/collections-csharp/StackInCSharp/StackInCSharp/Program.cs b/collections-csharp/StackInCSharp/StackInCSharp/Program.cs index d338b39118..ae44d762af 100644 --- a/collections-csharp/StackInCSharp/StackInCSharp/Program.cs +++ b/collections-csharp/StackInCSharp/StackInCSharp/Program.cs @@ -1,7 +1,8 @@ using StackInCSharp; using System.Collections; +using System.Collections.Concurrent; -var page1 = new Page("\nThe first visited page", DateTime.Now); +var page1 = new Page("The first visited page", DateTime.Now); var page2 = new Page("The second visited page", DateTime.Now); var nonGenericStackHelper = new NonGenericStackHelper(); @@ -46,8 +47,8 @@ result = genericStackHelper.TryPopItem(out topPage); Console.WriteLine($"\nTryPop() METHOD"); -Console.WriteLine($"TryPop returns: {result}"); -Console.WriteLine($"the title of the topPage in pageStack is: {topPage?.Title}"); +Console.WriteLine($"TryPop returns: {result}"); +Console.WriteLine($"the title of the topPage in pageStack was: {topPage?.Title}"); genericStackHelper.PrintCount(); nonGenericStackHelper.ClearStack(); @@ -61,4 +62,30 @@ Console.WriteLine($"Thread-safety for non-generic case"); Console.WriteLine($"{nameof(nonGenericStackHelper.NonGenericStack)} is thread-safe: {nonGenericStackHelper.IsSynchronizedStack(nonGenericStackHelper.NonGenericStack)}"); -Console.WriteLine($"{nameof(synchronizedStack)} is thread-safe: {nonGenericStackHelper.IsSynchronizedStack(synchronizedStack)}"); \ No newline at end of file +Console.WriteLine($"{nameof(synchronizedStack)} is thread-safe: {nonGenericStackHelper.IsSynchronizedStack(synchronizedStack)}"); + +Console.WriteLine($"\nConstructor ORDER"); +List letters = ["a", "b", "c"]; +Stack lettersFromList = new Stack(letters); +Console.WriteLine(lettersFromList.Peek()); +Console.WriteLine(string.Join(", ", lettersFromList)); + +Console.WriteLine($"\nEMPTY STACK"); +var undoStack = new Stack(); +Console.WriteLine($"Is the stack empty? {undoStack.Count == 0}"); + +undoStack.Push("Type 'Hello'"); +undoStack.Push("Make it bold"); +undoStack.Push("Delete a word"); + +while (undoStack.TryPop(out var action)) +{ + Console.WriteLine($"Undo: {action}"); +} + +Console.WriteLine($"Is the stack empty? {undoStack.Count == 0}"); + +Console.WriteLine($"\nConcurrentStack"); +var threadSafePageStack = new ConcurrentStack(); +Parallel.For(0, 100, i => threadSafePageStack.Push(new Page($"Page {i}", DateTime.Now))); +Console.WriteLine($"threadSafePageStack contains {threadSafePageStack.Count} items"); \ No newline at end of file diff --git a/collections-csharp/StackInCSharp/StackInCSharp/StackInCSharp.csproj b/collections-csharp/StackInCSharp/StackInCSharp/StackInCSharp.csproj index 74abf5c976..dfb40caafc 100644 --- a/collections-csharp/StackInCSharp/StackInCSharp/StackInCSharp.csproj +++ b/collections-csharp/StackInCSharp/StackInCSharp/StackInCSharp.csproj @@ -2,7 +2,7 @@ Exe - net6.0 + net10.0 enable enable diff --git a/collections-csharp/StackInCSharp/Tests/StackInCSharpUnitTests.cs b/collections-csharp/StackInCSharp/Tests/StackInCSharpUnitTests.cs index 38fd034e1b..dd16b316e3 100644 --- a/collections-csharp/StackInCSharp/Tests/StackInCSharpUnitTests.cs +++ b/collections-csharp/StackInCSharp/Tests/StackInCSharpUnitTests.cs @@ -151,4 +151,28 @@ public void GivenGenerickStack_WhenClear_ThenTheStackIsEmpty() Assert.Empty(_genericStackHelper.GenericStack); } + + [Fact] + public void GivenEmptyGenericStack_WhenTryPop_ThenItReturnsFalse() + { + var popped = _genericStackHelper.TryPopItem(out var page); + + Assert.False(popped); + Assert.Null(page); + } + + [Fact] + public void GivenEmptyGenericStack_WhenPeek_ThenItThrows() + { + Assert.Throws(() => _genericStackHelper.PeekItem()); + } + + [Fact] + public void GivenAList_WhenStackIsCreatedFromIt_ThenTheLastElementIsOnTop() + { + var stack = new System.Collections.Generic.Stack(["a", "b", "c"]); + + Assert.Equal("c", stack.Peek()); + Assert.Equal(["c", "b", "a"], stack.ToArray()); + } } \ No newline at end of file diff --git a/collections-csharp/StackInCSharp/Tests/Tests.csproj b/collections-csharp/StackInCSharp/Tests/Tests.csproj index 689c7b6d5a..487ed0bf05 100644 --- a/collections-csharp/StackInCSharp/Tests/Tests.csproj +++ b/collections-csharp/StackInCSharp/Tests/Tests.csproj @@ -1,20 +1,20 @@ - net6.0 + net10.0 enable false - - - + + + runtime; build; native; contentfiles; analyzers; buildtransitive all - + runtime; build; native; contentfiles; analyzers; buildtransitive all