ConstructorBuilder cb = tb.DefineConstructor(MethodAttributes.Public, CallingConventions.Standard, new Type[] { typeof(string)});
// Добавление кода для конструктора
ILGenerator il = cb.GetILGenerator();
il.EmitWriteLine("Constructor");
il.Emit(OpCodes.Ret);
// Непосредственное создание типа
tb.CreateType();
// Сохранение типа в файл
ab.Save("My1.dll");
Приведенный код при запуске создаст на диске файл My1.dll, в котором будет класс с 2-мя конструкторами, причем второй конструктор будет при вызове выводить строчку "Constructor".
Два пояснения по коду:
1. Очень часто при создании типов и членов этих типов надо указать их атрибуты (модификаторы доступа типа public и т. п.). Это мы делаем через перечисления TypeAttributes и MethodAttributes, которое содержит соответствующие значения (Public, например). Несколько необходимых значений из этих перечислений можно соединить через побитовое "или".
2. Метод Emit класса ILGenerator в качестве параметра принимает перечисление OpCodes, которое фактически содержит инструкции на языке IL - языке, который является аналогом для .NET обычного ассемблера. Это означает, что его инструкции не столь очевидны для реального программирования - именно поэтому в качестве примера таких IL-инструкций и была приведена самая простая из них - а именно выход из функции (OpCodes.Ret).