The syntax has improved quite substantially since 2016 for pattern matching at C#'s end, and it's very easy to model ADTs with records (and the experience of using them even before that was decent with methods accepting lambdas).
Today, you write it in a similar way you would write a match in Rust.
The other commenter is not technically wrong to point at “algebraic data types”, but I don’t think that answer is helpful at all. It’s like saying the answer to data modelling is tuples.
I would instead recommend searching for “functional programming and domain driven design”.
* Rust * Kotlin * Dart * Java
Yep, even Java. Check this out: https://blog.jdriven.com/2021/10/sealed-classes/