Roadmap › 1. .NET › Step 11
SO
SOLID Principles with Examples
The five SOLID principles with bad-vs-good C# code, plus DRY, KISS, YAGNI, dependency injection and how SOLID shows up in ASP.NET Core.
Quick revision for interview day. Print it or save it as a PDF.
SOLID in one table
| Principle | Smell | Fix | |
|---|---|---|---|
| S | Single Responsibility | God class, Manager/Utils | Split by reason to change |
| O | Open/Closed | Growing switch/if-else on type | Strategy/polymorphism + DI |
| L | Liskov Substitution | Override throws NotSupportedException; is checks | Fix the hierarchy; use interfaces/composition |
| I | Interface Segregation | Implementers leave methods empty | Split into role interfaces |
| D | Dependency Inversion | new ConcreteService() inside logic | Inject an abstraction |
DI lifetimes
| Instance per | Use for | |
|---|---|---|
| Transient | resolution | stateless, light |
| Scoped | request | DbContext, unit of work |
| Singleton | app | config, caches, thread-safe services |
Never inject scoped into singleton → use IServiceScopeFactory.
Other principles
- DRY — one source of truth for knowledge.
- KISS — simplest thing that works.
- YAGNI — don't build for imaginary futures.
- SoC — separate UI / business / data.
- Composition over inheritance.
- Law of Demeter — no
a.B.C.Dchains.
Quick code: DIP + OCP
csharp
public interface IExporter { string Format { get; } byte[] Export(Report r); }
public class PdfExporter : IExporter { public string Format => "pdf"; public byte[] Export(Report r) => ...; }
public class ExcelExporter : IExporter { public string Format => "xlsx"; public byte[] Export(Report r) => ...; }
public class ExportService(IEnumerable<IExporter> exporters)
{
public byte[] Run(Report r, string fmt) => exporters.Single(e => e.Format == fmt).Export(r);
}One-liners to say in the interview
- SRP: "A class should have one reason to change — one actor it serves."
- OCP: "Add new behaviour by adding classes, not by editing tested ones."
- LSP: "A subclass must work anywhere its base class is expected — no surprises."
- ISP: "Don't force clients to depend on methods they don't use."
- DIP: "High-level policy depends on abstractions; details plug in through DI."
- Balance: "I apply SOLID where change is likely; for simple, stable code I keep it simple."