Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:

Lec09

.pdf
Скачиваний:
7
Добавлен:
10.06.2015
Размер:
681.75 Кб
Скачать

Атрибуты

using System; namespace test{

[AttributeUsage(AttributeTargets.All, Inherited = false,

AllowMultiple = true)] //Объявление атрибута.

{

class TestAttribute : System.Attribute

private string name;

//Поле атрибута.

public TestAttribute(string name){//Конструктор атрибута.

this.name = name;

 

 

}

 

 

public virtual string Name{//Свойство только для чтения.

get{

 

 

return name;

 

 

}

 

 

}

 

 

}

 

 

//Конец объявления атрибута.

 

[TestAttribute("NAME")]

//Применение атрибута к классу.

class Test{

 

 

static void Main(){

 

 

GetAttribute(typeof(Test));

}

public static void GetAttribute(Type t){ TestAttribute att =

(TestAttribute)Attribute.GetCustomAttribute(t, typeof(TestAttribute));

Console.WriteLine("{0}", att.Name);

}}}

Результат:

NAME

21

Сериализация

Для того, чтобы класс стал сериализуемым, достаточно объявить его с атрибутом Serializable.

namespace Serial

{

[Serializable()] class Worker

{

public int age; public int id;

}

}

После этого экземпляр класса можно, например, целиком сохранять в файл и читать из файла (именно экземпляр класса целиком, а не поля класса по отдельности).

22

Сериализация

using System; using System.IO;

using System.Runtime.Serialization;

using System.Runtime.Serialization.Formatters.Binary; namespace Serial{

class Program{

static void Main(string[] args){

//Задаем экземпляр класса. Worker w = new Worker(); w.age = 22;

w.id = 2;

//Сериализуем класс.

FileStream fs = new FileStream("1.txt", FileMode.Create, FileAccess.Write);

IFormatter bf = new BinaryFormatter(); bf.Serialize(fs, w);

fs.Close();

// Десериализуем класс.

fs = new FileStream("1.txt", FileMode.Open, FileAccess.Read);

Worker w1 = (Worker)bf.Deserialize(fs); Console.WriteLine("age: " + w1.age + ", id: " + w1.id); fs.Close();

}}}

Результат: age: 22, yoe: 2

23

Nullable типы

Как известно,value-типы(к ним относятся,например, int, byte и другие)не могутприниматьзначениеnull.

Но иногдатакаяпотребностьвозникает.Например, при работе с базамиданных - в столбцетаблицымогутхранитсязначения целоготипа и, кроме того,могутдопускатьсянеопределенные значения(NULL).

Nullable-типы могут принимать,кроме собственнозначений соотвествующеготипа,значениеnull.

Пример:

Nullable n; n = null;

Упрощенныйсинтаксис:

int? n;

С точки зрения реализации все nullable-типы являются экземплярами структуры System.Nullable.

24

Рефлексия

Иногда нам требуется динамически создать некий код. Созданная динамически сборка может существовать только в памяти или же может быть сохраненной на диск в виде файла.

Сначала мы должны сгенерировать сборку, затем на основании этой сборки - модуль, потом на основании этого модуля - тип (например, класс), потом на основании этого типа (класса) - его члены (конструкторы, методы и т. п.). И, уже в самом конце, мы создаем непосредственно сгенерированный на предыдущих шагах тип.

25

Рефлексия

// Создание имени сборки.

AssemblyName an = new AssemblyName("MyAssembly"); an.Version = new Version("1.0.0.0");

//Создание сборки. AssemblyBuilder ab;

ab = AppDomain.CurrentDomain.DefineDynamicAssembly(an, AssemblyBuilderAccess.Save);

//Создание модуля в сборке.

ModuleBuilder mb = ab.DefineDynamicModule("MyModule", "My.dll"); // Создание типа в сборке.

TypeBuilder tb = mb.DefineType("MyClass", TypeAttributes.Public); // Создание конструктора без параметров.

ConstructorBuilder cb0 = tb.DefineConstructor(MethodAttributes.Public, CallingConventions.Standard, null);

//Добавление кода для конструктора. ILGenerator il0 = cb0.GetILGenerator(); il0.Emit(OpCodes.Ret);

//Создание конструктора с параметром типа string.

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("qqq.dll");

26

Применение пространства имен

Если вы подключили в проекте два пространстваимен, например ns1 и ns2,

using ns1; using ns2;

которыевключают в себя класс Class1, то при попытке создатьэкземпляр данного класса возникнет ошибка

Class1 c = new Class1();

Компилятор не знает, откуда создаватькласс:

из пространства имен ns1 или ns2. В таком случае надо конкретно указыватьпространство имен

ns1.Class1 c = new ns1.Class1();

27

Соседние файлы в предмете [НЕСОРТИРОВАННОЕ]