Menu
Coddy logo textTech

Арифметика указателей

Часть раздела Logic & Flow путешествия по C на Coddy — урок 9 из 63.

Вы узнали, как обращаться к элементам массива, используя указательную нотацию, такую как *(array + i). Теперь вы познакомитесь с еще более мощным методом: арифметика указателей, которая позволяет перемещать указатели по памяти с помощью простых операций инкремента и декремента.

Когда вы увеличиваете указатель с помощью ++ или уменьшаете его с помощью --, указатель не просто перемещается на один байт. Вместо этого он перемещается на размер типа данных, на который он указывает. Для целочисленного указателя ptr++ перемещается вперед на sizeof(int) байт, попадая точно на следующее целое число в памяти.

int numbers[5] = {10, 20, 30, 40, 50};
int *ptr = numbers;    // Указывает на первый элемент (10)
ptr++;                 // Теперь указывает на второй элемент (20)
ptr++;                 // Теперь указывает на третий элемент (30)

Этот автоматический расчет размера делает арифметику указателей такой мощной и удобной. Вам не нужно беспокоиться о вычислениях байтов — C берет на себя адресацию памяти за вас на основе типа данных указателя.

Арифметика указателей особенно полезна для обхода массивов в циклах. Вместо использования индексов массива вы можете инкрементировать указатель, чтобы последовательно перемещаться по каждому элементу, что часто приводит к более эффективному коду.

challenge icon

Задание

Легко

Напишите программу на языке C, которая демонстрирует арифметику указателей, используя операции инкремента указателя для обхода и обработки массива. Ваша программа должна:

  1. Объявить целочисленный массив с именем data из 5 элементов и инициализировать его значениями {12, 24, 36, 48, 60}
  2. Объявить указатель на целое число с именем ptr и инициализировать его так, чтобы он указывал на первый элемент массива
  3. Использовать цикл for, который выполняется 5 раз, для обхода всего массива, используя только арифметику указателей
  4. Внутри цикла:
    • Вывести текущее значение, на которое указывает ptr, используя оператор разыменования
    • Вывести адрес памяти, хранящийся в ptr, используя спецификатор формата %p
    • Увеличить указатель с помощью ptr++, чтобы перейти к следующему элементу
  5. После цикла сбросить ptr, чтобы он снова указывал на первый элемент массива
  6. Использовать арифметику указателей для прямого доступа и вывода третьего элемента (индекс 2), используя *(ptr + 2)
  7. Использовать арифметику указателей для прямого доступа и вывода последнего элемента (индекс 4), используя *(ptr + 4)

Ваш вывод должен отображать результаты в следующем формате:

Value: 12, Address: [address]
Value: 24, Address: [address]
Value: 36, Address: [address]
Value: 48, Address: [address]
Value: 60, Address: [address]
Third element: 36
Last element: 60

Эта задача проверяет ваше понимание того, как операции инкремента указателя автоматически перемещаются на размер типа данных, и как вы можете использовать арифметику указателей для доступа к элементам массива по определенным смещениям от базовой позиции указателя.

Шпаргалка

Арифметика указателей позволяет перемещать указатели по памяти с помощью операций инкремента и декремента. Когда вы увеличиваете указатель, он перемещается на размер типа данных, на который он указывает, а не на один байт.

Основные операции арифметики указателей:

int numbers[5] = {10, 20, 30, 40, 50};
int *ptr = numbers;    // Указывает на первый элемент (10)
ptr++;                 // Теперь указывает на второй элемент (20)
ptr++;                 // Теперь указывает на третий элемент (30)

Вы также можете использовать арифметику указателей для доступа к элементам по определенным смещениям:

*(ptr + 2)  // Доступ к элементу со смещением 2 от текущей позиции

Арифметика указателей полезна для обхода массивов в циклах, что часто приводит к более эффективному коду, чем использование индексов массива.

Попробуйте сами

#include <stdio.h>

int main() {
    // TODO: Напишите свой код здесь
    // Объявите и инициализируйте массив 'data' значениями {12, 24, 36, 48, 60}
    // Объявите указатель 'ptr' и инициализируйте его так, чтобы он указывал на первый элемент
    // Используйте цикл for с арифметикой указателей для обхода массива
    // Выведите каждое значение и адрес, затем увеличьте указатель
    // Сбросьте указатель и используйте арифметику указателей для доступа к конкретным элементам
    
    return 0;
}
quiz iconПроверьте себя

В этом уроке есть небольшой тест. Начните урок, чтобы ответить на вопросы и сохранить прогресс.

Все уроки раздела Logic & Flow