Неуправляемую dll можно подгружать динамически через LoadLibrary, указывая к ней путь.
Порядок примерно такой:
1. LoadLibrary с путём к dll.
2. GetProcAddress получает неуправляемый указатель на функцию в dll.
3. Marshal.GetDelegateForFunctionPointer преобразует неуправляемый указатель на функцию в делегата, который можно использовать обычным для c# способом.
4. FreeLibrary завершает работу с dll.
Подробнее и с примером
Ну а с управляемыми нужно работать через класс Assembly.
Например, загрузка сборки — Assembly.LoadFrom(string)