Занятие №7 на курса по програмиране на C# 2013 провеждан от ДАВИД академия в ПМГ "Никола Обрешков" - Казанлък. Включва темите:
- Свойства
- Индексатори
- Наследяване
- Изключения
3. Какво ще бъде изведено в конзолата?
class Book
{
private string _title;
public Book(string title)
{
_title = title;
}
}
class Program
{
static void Main(string[] args)
{
Book book1 = new Book("The Hobbit");
Book book2 = new Book("The Hobbit");
Console.WriteLine(book1 == book2);
}
}
4. Къде е проблемът в кода?
class Person
{
public string FirstName;
public string LastName;
public Person(string firstName, string lastName)
{
this.FirstName = firstName;
this.LastName = lastName;
}
}
5. Къде е проблемът в кода?
class Institution
{
private string _name;
private string _address;
public Institution(string name)
{
_name = name;
}
public Institution(string address)
{
_address = address;
}
public string GetName()
{
return _name;
}
public string GetAddress()
{
return _address;
}
}
6. Къде е проблемът в кода?
class Animal
{
private static int _animalCount;
private readonly string _species;
static Animal(int initialCount)
{
_animalCount = initialCount;
}
public Animal(string species)
{
this._animalCount++;
_species = species;
}
}
7. Свойства
• Какво е „свойство“?
– Член, с който се борави, както с поле
– Не се асоциира с част от паметта на обекта
– Не съхранява характеристики на обекта, но може да
служи за достъпването им
– Тип данни и наименование
– Уникалност на наименованието
– Много удобно при капсулиране
8. Свойства
• Деклариране на свойства
– Тип данни
– Наименование – съществително или фраза в Pascal
case
– Тяло – блок, съдържащ поне един от следните
блокове:
• Блок за четене – префиксира се със служебната дума get и
задължително връща стойност
• Блок за записване – префиксира се със служебната дума set
и в него може да се използва служебната дума value за
достъпване на присвоената стойност
9. Свойства
class Dog
{
private string _name;
private string _breed;
public string Name
{
get { return _name; }
}
public string Breed
{
get { return _breed; }
set { _breed = value; }
}
public string Description
{
get { return string.Format("{0} is a {1}.", _name, _breed); }
}
}
10. Свойства
• Пред блоковете за четене или записване може
да бъдат поставени модификатори за достъп
public string Name
{
get { return _name; }
protected set { _name = value; }
}
• Позволява различни нива на видимост за двете
операции
11. Свойства
• Използване на свойства – аналогично с
използването на полета
Dog dog = new Dog();
dog.Breed = "poodle";
Console.WriteLine(dog.Description);
12. Свойства
• Автоматично генерирани свойства
– Кодът в тялото им не се декларира от програмиста
– Компилаторът създава служебно поле за съхранение
на данните
– Удобни за капсулиране на полета – всички полета
трябва да са частни
13. Свойства
• Деклариране на автоматично генерирани
свойства
– Вместо блокове за четене и записване се поставят
само двете служебни думи get и set с точка и запетая
след всяка от тях
– Задължително трябва да присъстват и двете служебни
думи
– Могат да се използват модификатори за достъп
class Dog
{
public string Name { get; protected set; }
public string Breed { get; set; }
}
14. Свойства
• Статични свойства
– Не са обвързани с конктрена инстанция на класа, а
със самия клас
– В блоковете за четене и записване не могат да се
използват пряко нестатични членове на класа
– Декларират се с ключовата дума static
– Също могат да са автоматично генерирани
15. Свойства
class Animal
{
private static int _animalCount = 0;
public static int AnimalCount
{
get { return _animalCount; }
set { _animalCount = value; }
}
}
// Използване на статично свойство
Console.WriteLine(Animal.AnimalCount);
16. Индексатори
• Какво е „индексатор“?
– Член, служещ за презаписване на оператора за
достъпване на индексиран елемент []
– Един или повече параметри; тип на връщания
резултат
– Повече от един индексатори с различни параметри
– Няма статични индексатори
17. Индексатори
• Деклариране на индексатори
Сходно с декларирането на свойства
Тип данни на индексирания елемент
Ключова дума this
Списък от един или повече параметри, заградени в
квадратни скоби
– Тяло – блок с блокове за четене и/или запис
–
–
–
–
18. Индексатори
class Dogs
{
private readonly Dog[] _dogs = new Dog[50];
public Dog this[int index]
{
get { return _dogs[index]; }
set { _dogs[index] = value; }
}
public Dog this[string name]
{
get
{
foreach (Dog dog in _dogs)
{
if (dog != null && dog.Name == name)
return dog;
}
return null;
}
}
}
19. Индексатори
• Използване на индексатори
– Сходно с индексирането на елементите на масив
– След променливата/израза се поставя списък от
аргументи в квадратни скоби
Dogs dogs = new Dogs();
dogs[0] = new Dog("Lassie");
Console.WriteLine(dogs["Lassie"].Description);
20. Наследяване
• Какво е „наследяване“?
– Друг от основните принципи на ООП
– Един клас може да наследи друг (родителски)
– Наследеният клас придобива всички членове на
родителския
– Наследеният клас може да декларира собствени
членове
– Част от членовете на родителския клас може да са
недостъпни за наследения заради видимостта си
– Множествено наследяване – в C# няма
– Дървовидни йерархии от класове
– Класът object – прародител на всички типове данни
21. Наследяване
• Деклариране на наследен клас
– Между наименованието на класа и тялото с
декларации на членовете му се поставя
двоеточие, следвано от наименованието на
родителския клас
class Organism
{
}
class Animal : Organism
{
}
22. Наследяване
• Конструктори на наследен клас
– По подразбиране изпълняват конструктора без
параметри на родителския клас
– Може да се посочи кой конструктор на родителския
клас да се изпълни – ключовата дума base и списък от
аргументи преди тялото на конструктора
23. Наследяване
class Organism
{
private readonly bool _needsOxygen;
public Organism(bool needsOxygen)
{
_needsOxygen = needsOxygen;
}
public bool NeedsOxygen
{
get { return _needsOxygen; }
}
}
24. Наследяване
class Animal : Organism
{
private readonly bool _isHerbivorous;
public Animal(bool isHerbivorous)
: base(true)
{
_isHerbivorous = isHerbivorous;
}
public bool IsHerbivorous
{
get { return _isHerbivorous; }
}
}
25. Наследяване
class Dog : Animal
{
private readonly string _name;
public Dog(string name)
: base(false)
{
_name = name;
}
public string Name
{
get { return _name; }
}
}
26. Наследяване
• Използване на наследени класове
– Обектите от наследен клас съдържат членовете,
декларирани в този клас, както и тези, декларирани в
родителските класове нагоре по йерархията
– Някои от тези членове може да са с ограничена
видимост
Dog dog = new Dog("Bolt");
if (dog.NeedsOxygen)
{
Console.WriteLine(
"{0} needs oxygen to survive.", dog.Name);
}
27. Наследяване
• Какво е превръщане на типове нагоре по
йерархията (upcasting)?
– Променлива с тип данни родителски клас
– Присвояваме израз с тип данни наследен клас
– Обектите от наследения клас винаги са съвместими с
родителския клас
– Извършва се неявно
Animal animal = new Dog("Шаро");
28. Наследяване
• Какво е превръщане на типове надолу по
йерархията (downcasting)?
– Променлива с тип данни наследен клас
– Присвояваме израз с тип данни родителски клас
– Грешка, ако обектът в паметта не е съместим с
наследения клас (неговият тип данни трябва да
съвпада с този наследен клас или да го наследява)
– Извършва се явно
Animal animal = new Dog("Шаро");
Dog dog = (Dog)animal;
29. Наследяване
• Безопасно превръщане на типове
– Операторът is
– Връща true, когато типът на стойността на израза
отляво съвпада с типа отдясно или го наследява
if (animal is Dog)
{
Dog dog = (Dog)animal;
// операции
}
30. Наследяване
• Безопасно превръщане на типове
– Операторът as
– Превръща типа на стойността отляво към типа
отдясно, когато типовете са съвместими
– Връща null, когато типовете не са съвместими
– Не може да се използва за нереферентни типове
Dog dog = animal as Dog;
if (dog != null)
{
// операции
}
31. Изключения
• Какво е „изключение“?
– Обект
– Сигнализира за проблем в изпълнението на
програмата (изключителна ситуация)
– Съдържа информация за вида на проблема и
състоянието на програмата при възникването му
– Прекратява се изпълнението на текущия код
– Търси се блок за обработка на изключения, който да
го обработи
– Ако не бъде обработено, преустановява се
изпълнението на програмата с грешка
32. Изключения
• Блокове за обработка на изключения
– Предоставят механизъм за обработка на изключения
– Операции, възникналите изключения в които да бъдат
обработени
– Операции за обработка на изключения
– Операции, които да бъдат изпълнени независимо от
възникването на изключения
33. Изключения
• Изключения в C#
– Базов клас за всички изключения – Exception
– Вградени класове за изключения, например
ArgumentException, IndexOutOfRangeException и
IOException
– Декларирани от програмиста класове за изключения
– наименованията им завършват с Exception
34. Изключения
• Класът Exception
– Message – съобщение за проблема в свободен текст
– StackTrace – състояние на стека от извиквания на
функции при възникването на изключението
– InnerException – вложено изключение
36. Изключения
class Dog
{
private readonly string _name;
public Dog(string name)
{
if (string.IsNullOrEmpty(name))
{
throw new ArgumentException(
"Every self-respecting dog should have a name.");
}
_name = name;
}
public string Name
{
get { return _name; }
}
}
37. Изключения
• Обработка на изключения – try...catch...
finally блокове
try
{
// Операции
}
catch (ArgumentException ex)
{
// Обработване на ArgumentException
}
catch (Exception ex)
{
// Обработване на Exception
}
finally
{
// Операции, които да винаги ще бъдат изпълнени
}
38. Изключения
• Възможно е при обработката на изключение да
се предизвика друго изключение, както и да се
предизвика същото отново
Organism organism = new Organism(true);
try
{
Animal animal = (Animal)organism;
}
catch (InvalidCastException ex)
{
Console.WriteLine("The organism is not an animal.");
throw;
}
39. Изключения
• Задължително изпълняване на операции,
независимо от възникването на изключения
FileStream fileStream = File.OpenRead(@"C:File.txt");
try
{
// Операции
}
finally
{
fileStream.Close();
}