Базовий курс програмування на С++. Урок 16. Вказівники, посилання (частина 2) |
Написав Joker | |||||
Неділя, 31 січня 2016 19:06 Переглядів: 9657
|
|||||
Життя належить тобі, і не буде для тебе нічого неможливого, якщо ти дійсно цього захочеш. (с) Марк Леві Сьогодні ми вивчимо 1. Посилання 2. Вказівники і функції 3. Посилання і функції 4. Оператори new і delete 5. Вказівники на вказівники 6. Домашнє завдання
Посилання Посилання частково схожі на вказівники, але є декілька суттєвих відмінностей. По-перше, посилання завжди працює тільки з одним значенням. Воно пов’язане з об’єктом на яке посилається і не може посилатися на будь-який інший. При створенні завжди обов’язкова ініціалізація. Створюється посилання за допомогою вже знайомого нам оператора &. Давайте продемонструємо це на прикладі. Створивши посилання int &p = a, ми не можемо десь у подальшому коді програми створити іншу змінну, припустимо int b = 15; і сказати, щоб &p = b. Це призведе до помилки! Але це все дає ще одну можливість керувати змінною. Достатньо просто використовувати її як і звичайну змінну. Якщо додати у попередню програму такий рядок: p = 99; То змінна a досі буде такою самою як і p, але їхні значення зміняться на 99.
Вказівники і функції Досі функції не повністю керували нашими даними. Наприклад ось такий код не може змінити значення a. А в багатьох ситуаціях нам буде потрібно, щоб функції могли змінювати значення змінних, а не створювати копії. До речі, з масивами все не так. Згадайте, що поєднує масиви і вказівники . Ось програма яка це доводить: Ну добре, ми відхилилися від теми. Так от, наше завдання полягає у тому, щоб функцію змінила початкове значення змінної a з функції main. У нас є два варіанти. Перший – за допомогою вказівників. Реалізувати це можна так: У функції main потрібно передати адресу змінної, а у func працюємо з вказівниками. Така функція змінила значення a = 19 на a = 20.
Посилання і функції Тепер спосіб 2. Він дещо простіший з вигляду. Просто потрібно пам’ятати: - Можна змінювати значення змінної за допомогою посилання.
У такому варіанті нам не потрібно використовувати всюди значок * . В цьому випадку параметром є посилання. Посилання дає доступ із функції до фактичних параметрів і може змінювати їх. Як на мене таке використання посилань є більш поширеним і потрібним, ніж їхня можливість керувати змінними у функції main. Але це ще не вершина! Посилання можна використовувати не тільки як параметри функцій, а й у ролі результатів функції. Тут є один підводний камінь. Функції можуть повертати посилання на об’єкт, якщо той існує в той час коли функція неактивна. Для цього перед іменем функції ставимо знак &. Давайте напишемо програму, яка визначить мінімальний елемент масиву і замінить його на -1 використовуючи посилання як результат роботи функції. Спершу ми створили масив і заповнили його випадковими числами від 15 до 115. Функція Find_minimum приймає масив та його розмір, це все, що нам потрібно для роботи. Результатом функції є посилання на мінімальний елемент масиву. Find_minimum(a,size) = -1; Тут присвоюємо мінімуму значення -1. І виводимо новий масив, де змінився тільки один елемент.
Оператори new і delete Тут ми навчимося одному із способів створювати масив, не знаючи його максимального розміру, у розумних межах. Зацікавило? У розумних межах означає, що обмеження все ж є, але про них пізніше. Спершу треба виділити пам’ять, де зберігати дані. Це робиться так int *p = new int; Це звісно для типу int, для інших типів аналогічно. Оператор new повертає адресу на вільне і доступне для використання місце у пам’яті. А адреси можна зберігати у вказівниках. Тому ми і створили вказівник у який записали адресу виділену оператором new. Тепер важливий момент: якщо ми змінимо адресу вказівника, то втратимо можливість працювати з виділеною пам’ятю! Щоб даремно не використовувати пам’ять, коли вона вже нам не потрібно потрібно її звільнити. Це робиться за допомогою delete. Завжди варто звільняти пам’ять. Тому візьміть собі за правило, якщо ви написали new, то десь має бути і delete. delete p; Ми звільнили пам’ять на яку посилався вказівник p, при цьому сам вказівник існує і можна ним користуватися. Щодо небезпек, ось приклад як втратити доступ до виділеної пам’яті. // Неправильний код!!!! int *p = new int; int a = 5; p = &a; // Немає delete В кінці змінено адресу вказівника p, тепер він посилається на змінну a, а не на виділену пам’ять. І до того ж немає оператора delete. Наше завдання: помножити два числа, взагалі не використовуючи змінних. Це доволі просто, спробуйте самі. Так, тепер поговоримо про масиви довільного розміру, це там значення розміру не повинно бути константою. Для прикладу створимо масив цілих чисел з 10 елементів. int *ar = new int [10]; І якщо є new, треба якось звільнити пам’ять, але для цілого масиву. Це робиться так delete [] ar; Все J Давайте ще один приклад, простенький. Знайдемо суму всіх елементів масиву заповненого випадковими числами від -78 до 78. Це все можна реалізувати і без використання змінних взагалі, що б ви подумали якби вам таке сказали декілька уроків тому?
Вказівники на вказівники Звучить погрозливо, але тут нічого складного немає. Якщо звичайний вказівник зберігає адресу змінної, то вказівник на вказівник зберігає адресу вказівника, що вказує на змінну. Щоб отримати значення змінної за допомогою такого вказівника потрібно його розіменувати двічі. Наприклад така програма: Важливо пам’ятати, що адреса вказівника не така сама як і адреса змінної на яку він посилається. Просто у частині пам’яті з його ім’ям зберігається адреса іншого об’єкта.
Домашнє завдання 1. Написати калькулятор без використання змінних ( 13 Проголосувало ) Новіші матеріали:
Старіші матеріали:
3.26 Copyright (C) 2008 Compojoom.com / Copyright (C) 2007 Alain Georgette / Copyright (C) 2006 Frantisek Hliva. All rights reserved." |