
Болтушкин Л.С., группа 712-2, лабораторная 4.docx
.pdfМинистерство науки и высшего образования Российской Федерации Федеральное государственное бюджетное образовательное учреждение высшего образования
ТОМСКИЙ ГОСУДАРСТВЕННЫЙ УНИВЕРСИТЕТ СИСТЕМ УПРАВЛЕНИЯ И РАДИОЭЛЕКТРОННИКИ (ТУСУР)
Кафедра комплексной информационной безопасности электронно-
вычислительных систем (КИБЭВС)
УКАЗАТЕЛИ И ССЫЛКИ Отчет по лабораторной работе №4
по дисциплине «Языки программирования»
Студент гр. 712-2
___________ Л.С. Болтушкин
__________
Руководитель Младший научный
сотрудник кафедры КИБЭВС
_______ __________ А.В. Куртукова
__________
Томск 2024
Введение
Целью данной лабораторной работы является изучение механизмов
работы указателей и ссылок.
Задание:
1.Изучить краткие теоретические сведения.
2.Подготовить примеры использования указателей и ссылок для языка
C++ и языка программирования, определенного выбранным вариантом –
Python, также сравнить возможности языков.
3. Продемонстрировать разницу между типизированными и нетипизированными указателями, разницу между указателями на данные и на функции, разницу между указателем и указуемым объектом, разницу между указателями-константами и указателями на константу, особенности работы с многоуровневыми указателями, разницу между указателями и ссылками.
2

1 Ход работы
1.1Программа на С++
Вданной лабораторной работе было написано два кода, на таких языках программирования как, Python (выбранный язык программирования) и С++ (по условию задания язык программирования).
Всамом начале работы была создана программа на языке программирования C++, демонстрирующая работу указателей и ссылок.
Часть программы, показывающая разницу между типизированными и нетипизированными указателями (рисунок 1.1).
Рисунок 1.1 – Разница между типизированными и нетипизированными указателями
Часть программы, показывающая разницу между указателями на функции и указателями на данные (рисунок 1.2).
Рисунок 1.2 – Разница между указателями на функцию и на данные
Можно заметить, что для указателей на функции определена операция вызова функции.
3

Далее следует часть программы, демонстрирующая разницу между указателями и указуемыми объектами (рисунок 1.3).
Рисунок 1.3 – Разница между указателями и указуемыми объектами
На следующем этапе работы была создана часть программы,
показывающая разницу между указателями-константами и указателями на константы (рисунок 1.4).
Рисунок 1.4 – Разница между указателями-константами и указателями на константы
Отличие заключается в том, что указатель-константа, в отличие от указуемого объекта нельзя изменять. Сам же указатель в данном случае может изменяться.
Далее были рассмотрены особенности работы с многоуровневыми указателями (рисунок 1.5).
Многоуровневые указатели представляют из себя указатели на указатели. В результате разыменования таких указателей получается адрес,
который хранится в указателе уровнем ниже.
Рисунок 1.5 – Особенности работы с многоуровневыми указателями
4

На последнем этапе нужно было показать разницу между указателями и ссылками (рисунок 1.6).
Рисунок 1.6 – Разница между указателями и ссылками
Результаты работы программы на языке программирования С++ (рисунок 1.7).
Рисунок 1.7 – Результат работы программы C++
Написанный код программы представлен в приложение А.
5

1.2 Программа на Python
Далее необходимо было написать аналогичную программу на выбранном языке программирования – Python. Стоит заметить, что в данном языке отсутствуют указатели, а также работа с адресами происходит иначе,
чем в С++.
Вязыке программирования Python все объекты делятся на изменяемые
инеизменяемые. При изменении значения неизменяемого объекта происходит его пересоздание. В связи с этим новый объект имеет другой адрес. При попытке редактирования изменяемого объекта пересоздание не производится,
поэтому адрес остается таким же, каким был изначально.
Рассмотрим особенности работы с объектами в Python (рисунок 1.8).
Рисунок 1.8 – Особенности работы с объектами в Python
Несмотря на тот факт, что в языке программирования Python
отсутствуют указатели, их все равно можно сымитировать. Данное действие осуществляется с помощью изменяемых объектов (рисунок 1.9).
Рисунок 1.9 – Изменение списков
6

В языке программирования Python возможно реализовать указатели,
используя встроенную библиотеку ctypes (рисунок 1.10).
Рисунок 1.10 – Использование встроенной библиотеки
Результаты работы программы на языке программирования Python
(рисунок 1.11).
Рисунок 1.11 – Результат работы программы Python
Написанный код программы представлен в приложение Б.
7
Заключение
В результаты выполнения данной лабораторной работы были получены знания о механизмах работы указателей и ссылок.
8
Приложение А
(обязательное)
#include <iostream> using namespace std;
int multiplier(int digit)
{
int result = digit * 100; return result;
} |
|
|
|
int main() |
|
|
|
{ |
|
|
|
int x = |
10; |
|
|
int y = |
20; |
|
|
cout << |
"#1" |
<< endl; |
|
int* ptr_1 = |
&x; //типизированный |
||
void* ptr_2 = &y; //нетипизированный, потому что void и он может указывать на |
|||
любой тип |
|
|
|
cout << |
"x = |
" << *ptr_1 << endl; |
|
cout << |
"y = |
" << y |
<< endl; |
cout << |
"x address: " << ptr_1 << endl; |
||
cout << |
"y address: " << ptr_2 << endl << endl; |
||
cout << |
"#2" |
<< endl; |
|
int (*ptr_f) |
(int); // объявление указателя на функцию |
||
ptr_f = |
multiplier; // присваивание указателю |
||
cout << |
"pointer to a function: " << ptr_f(y) << endl; |
||
cout << |
"pointer to data: " << *ptr_1 << endl << endl; |
||
cout << |
"#3" |
<< endl; |
|
cout << |
"pointer to x: " << ptr_1 << ", x = " << x << endl; // перевод строки |
||
cout << |
"pointer to y: " << ptr_2 << ", y = " << y << endl << endl; // два |
||
перевода строки для разделения вывода |
|||
cout << |
"#4" |
<< endl; |
const int cnst_x = 123; // указатель-константа const int* ptr_cnst = &y; // указатель на константу
cout << |
"constant-pointer to y: " << ptr_cnst << ", y = " << *ptr_cnst << endl; |
y = y * |
100; |
cout << |
"constant-pointer to new y: " << ptr_cnst << ", y = " << *ptr_cnst << |
endl; |
|
const int* ptr_to_cnst = &cnst_x; |
|
cout << |
"constant address: " << ptr_to_cnst << ", constant: " << *ptr_to_cnst << |
endl << endl; |
|
cout << |
"#5" << endl; |
int** multi_ptr = &ptr_1; // создается указатель на указатель |
|
cout << |
"pointer to a pointer: " << multi_ptr << endl; |
cout << |
"pointer to a value : " << ptr_1 << endl; |
cout << |
"value: " << **multi_ptr << endl << endl; // вывод значения x, доступ |
получив как раз через многоуровневый ук-ль |
|
cout << |
"#6" << endl; |
int& link = y; // объявление ссылки |
|
cout << |
"pointer to y: " << ptr_2 << endl; // вывод y через указатель |
cout << |
"link to y: " << link << endl; // а тут уже через ссылку |
link += |
100; |
cout << |
"link was changed: " << link << endl; |
} |
|
|
9 |
Приложение Б
(обязательное)
print("#1") x = 10
print(f"x = {x}\naddress x: {id(x)}") x *= 20
print(f"changed x = {x}\naddress x: {id(x)}\n") #Адрес в памяти lst = [2, 0, 2, 2]
print(f"list = {lst}\nlist address: {id(lst)}") lst.append(x)
print(f"changed list = {lst}\nchanged list address: {id(lst)}\n")
print("#2")
ptr = [x] #создание списка, иметируя указатель print(f"address of the x: {id(ptr)}\nx = {ptr[0]}") ptr[0] += 10 #увеличение на 10 первого элемента списка
print(f"address of the changed x: {id(ptr)}\nx = {ptr[0]}\n")
print("#3")
from ctypes import * i = c_int(42)
ptr = pointer(i) #указатель на i
print(f"i = {i}\npointer to i: {ptr}\npointer dereference: {ptr.contents}\n") ptr2 = pointer(ptr)
print(f"multilevel pointer: {ptr2}\nmultilevel pointer dereference:{ptr2.contents.contents}") #многоуровневый укзатель
10