Making methods abstract ensures that all inherited classes implement that particular property. This is done most commonly when all inherited classes need/should have different behaviors than the parent class.
Let's say we have this DoMorningRounds method in the Employee class.
If we leave the method header like this, every Employee in the Zoo will clean cages if this method is called on them. But we have many different Employee types that should do something different when they're doing their morning rounds; human resources people should go through their mail box, attendants should check supplies, etc. We could make the method virtual and then override the method in any descendant classes, but what if we forget to override the DoMorningRounds in the Boss class and we call the method on a Boss object? The Boss would be cleaning cages and as hilarious as that might be, it is not the intended behavior of a Boss.
A solution to this problem is to make the parent class's DoMorningRounds method abstract. What this means is that all Employee types have an idea of what doing morning rounds is, but the implementation of what that specifically is is dependent on the type. Making methods abstract also ensures that all descendant classes have to have that method implemented. This keeps us from running into problems with virtual. To make a method abstract we will insert the abstract keyword to the right of the visibility.
When we do this we get a number of errors. The first one we will fix is CS0500. This error means, "your Employee class has an idea of a method, but you're doing something with this idea and you can't". So what we will do is remove the method body and make the method a "stub".
The CS0500 error now goes away. We still have errors, though, saying that we have this "idea" but nothing is using it. This is much like being in a meeting and the leader saying, "Hey, we should all do this thing!" and then everyone stares at them blankly. Each of the descendant classes need to declare methods and method bodies that do their own "version" of that method.
Once we add an override to a descendant class, the error will go away for that class.
Now that all descendant classes implement DoMorningRounds all errors will go away. Then, if we call DoMorningRounds on different Employee types, they will have their own unique "version" of that method. For example, when I call DoMorningRounds on the Boss object...
...and press F11, the debugger will step into the Boss class's DoMorningRounds method and our Boss no longer has to worry about cleaning cages and we've ensure they are doing what a Boss is supposed to do.