TinyOptional 2.1.0
dotnet add package TinyOptional --version 2.1.0
NuGet\Install-Package TinyOptional -Version 2.1.0
This command is intended to be used within the Package Manager Console in Visual Studio, as it uses the NuGet module's version of Install-Package.
<PackageReference Include="TinyOptional" Version="2.1.0" />
For projects that support PackageReference, copy this XML node into the project file to reference the package.
<PackageVersion Include="TinyOptional" Version="2.1.0" />
<PackageReference Include="TinyOptional" />
For projects that support Central Package Management (CPM), copy this XML node into the solution Directory.Packages.props file to version the package.
paket add TinyOptional --version 2.1.0
The NuGet Team does not provide support for this client. Please contact its maintainers for support.
#r "nuget: TinyOptional, 2.1.0"
#r directive can be used in F# Interactive and Polyglot Notebooks. Copy this into the interactive tool or source code of the script to reference the package.
#:package TinyOptional@2.1.0
#:package directive can be used in C# file-based apps starting in .NET 10 preview 4. Copy this into a .cs file before any lines of code to reference the package.
#addin nuget:?package=TinyOptional&version=2.1.0
#tool nuget:?package=TinyOptional&version=2.1.0
The NuGet Team does not provide support for this client. Please contact its maintainers for support.
TinyOptional
![]()
Express the presence or absence of a value without null. Zero ceremony, clean chaining, no exceptions by surprise.
dotnet add package TinyOptional
Creating an Optional
using TinyOptional;
Optional<string>.Of("hello") // non-null value — throws if null
Optional<string>.OfNullable(maybeNull) // wraps null as empty
Optional<string>.Empty() // explicitly empty
Getting the value out
optional.OrElse("default") // fallback value
optional.OrElseGet(() => ComputeDefault()) // fallback computed lazily
optional.OrElseNull() // returns T? — null if empty
optional.OrElseDo(() => Log("nothing here")) // run side effect if empty
optional.Get() // throws if empty
optional.GetOrThrow(() => new NotFoundException())
Transforming
optional
.Where(x => x.Length > 0) // filter — empty if predicate fails
.Select(x => x.ToUpper()) // map — stays empty if already empty
.SelectMany(x => Parse(x)) // flatmap — avoids Optional<Optional<T>>
.OrElse("FALLBACK")
Async variants: .WhereAsync(...), .SelectAsync(...)
Collapsing to a value
var label = optional.Match(
onPresent: name => $"Hello, {name}",
onEmpty: () => "Hello, stranger"
);
Side effects
optional
.IfPresent(v => Console.WriteLine($"Got: {v}"))
.OrElse(() => Console.WriteLine("Nothing"));
optional
.IfNotPresent(() => Console.WriteLine("Nothing"))
.OrElse(v => Console.WriteLine($"Got: {v}"));
Async variants: .IfPresentAsync(...), .IfNotPresentAsync(...)
LINQ integration
optional.ToEnumerable() // IEnumerable<T> with 0 or 1 element
// works in query expressions and SelectMany chains
var results = from opt in listOfOptionals
from value in opt.ToEnumerable()
select value;
Equality
Two optionals are equal when both are empty, or both are present with equal values:
Optional<int>.Of(42) == Optional<int>.Of(42) // true
Optional<int>.Empty() == Optional<int>.Empty() // true
Optional<int>.Of(1) == Optional<int>.Of(2) // false
Collection extensions
All return Optional<T> instead of throwing or returning null:
list.FirstIfExists() // first element, or empty
list.FirstIfExists(x => x.IsActive) // first match, or empty
list.LastIfExists() // last element, or empty
list.LastIfExists(x => x.IsActive) // last match, or empty
list.SingleIfExists() // the only element — empty if 0 or 2+
list.SingleIfExists(x => x.IsActive) // the only match — empty if 0 or 2+
list.ElementAtIfExists(3) // safe index access
list.AggregateIfExists(seed, func) // empty if source is null or empty
String extension
"hello".IfAny() // Optional<string> with value
"".IfAny() // empty Optional
((string?)null).IfAny() // empty Optional
MIT License
| Product | Versions Compatible and additional computed target framework versions. |
|---|---|
| .NET | net5.0 was computed. net5.0-windows was computed. net6.0 was computed. net6.0-android was computed. net6.0-ios was computed. net6.0-maccatalyst was computed. net6.0-macos was computed. net6.0-tvos was computed. net6.0-windows was computed. net7.0 was computed. net7.0-android was computed. net7.0-ios was computed. net7.0-maccatalyst was computed. net7.0-macos was computed. net7.0-tvos was computed. net7.0-windows was computed. net8.0 was computed. net8.0-android was computed. net8.0-browser was computed. net8.0-ios was computed. net8.0-maccatalyst was computed. net8.0-macos was computed. net8.0-tvos was computed. net8.0-windows was computed. net9.0 was computed. net9.0-android was computed. net9.0-browser was computed. net9.0-ios was computed. net9.0-maccatalyst was computed. net9.0-macos was computed. net9.0-tvos was computed. net9.0-windows was computed. net10.0 was computed. net10.0-android was computed. net10.0-browser was computed. net10.0-ios was computed. net10.0-maccatalyst was computed. net10.0-macos was computed. net10.0-tvos was computed. net10.0-windows was computed. |
| .NET Core | netcoreapp3.0 was computed. netcoreapp3.1 was computed. |
| .NET Standard | netstandard2.1 is compatible. |
| MonoAndroid | monoandroid was computed. |
| MonoMac | monomac was computed. |
| MonoTouch | monotouch was computed. |
| Tizen | tizen60 was computed. |
| Xamarin.iOS | xamarinios was computed. |
| Xamarin.Mac | xamarinmac was computed. |
| Xamarin.TVOS | xamarintvos was computed. |
| Xamarin.WatchOS | xamarinwatchos was computed. |
Compatible target framework(s)
Included target framework(s) (in package)
Learn more about Target Frameworks and .NET Standard.
-
.NETStandard 2.1
- No dependencies.
NuGet packages
This package is not used by any NuGet packages.
GitHub repositories
This package is not used by any popular GitHub repositories.