Ideally you'd want to prevent the problem by ensuring that you already know the type of your objects. If you have an object, you don't know its type, and you have to inspect it to see if it's a Truck or a Vehicle and see which properties it has, that's the underlying problem to solve. You don't want a method to take an object and then try to figure out what it is. Instead, fix it so that the type of the parameter is meaningful and tells the method everything that it needs to know about that parameter.
Without knowing the full details, you could try something like this:
public interface IVehicle
{
decimal Height {get;}
}
This interface has the properties you expect. You write all your code using this interface.
Dictionary<string, IVehicle> vehicles
From now on, you never have to wonder what something is or which properties it has. It's an IVehicle, which tells you that it has all of the properties of IVehicle.
You still have the original problem - other classes that don't implement this interface. You can adapt then so that they do implement the interface. For example,
public class TruckToVehicleAdapter : IVehicle
{
private readonly Truck _truck;
public TruckToVehicleAdapter(Truck truck)
{
_truck = truck;
}
public decimal Height { get { return _truck.WhateverHeightPropertyThisHas; } }
}
That's just one approach. But the general idea is to avoid having a bunch of objects where you don't know their types. Instead, think of how to take the object you have and require it to be the type you want. Convert it, make a new object, write an adapter like in the above example. But then you'll know what you have.
And if another new type of object comes along you won't have to modify all your methods to see if your object is a Motorcycle or a RecreationalVehicle. That can get out of hand. You can just follow the same pattern. Make everything an IVehicle.
Vehicle?var xy = x as Y; if(x != null)...BS...