Книга: Язык программирования Си. Издание 3-е, исправленное
5.9 Указатели против многомерных массивов
5.9 Указатели против многомерных массивов
Начинающие программировать на Си иногда не понимают, в чем разница между двумерным массивом и массивом указателей вроде name из приведенного примера. Для двух следующих определений:
int a[10][20];
int *b[10];
записи a[3][4] и b[3][4] будут синтаксически правильным обращением к некоторому значению типа int. Однако только a является истинно двумерным массивом: для двухсот элементов типа int будет выделена память, а вычисление смещения элемента a[строка][столбец] от начала массива будет вестись по формуле 20 * строка + столбец, учитывающей его прямоугольную природу. Для b же определено только 10 указателей, причем без инициализации. Инициализация должна задаваться явно -либо статически, либо в программе. Предположим, что каждый элемент b указывает на двадцатиэлементный массив, в результате где-то будут выделены пространство, в котором разместятся 200 значений типа int, и еще 10 ячеек для указателей. Важное преимущество массива указателей в том, что строки такого массива могут иметь разные длины. Таким образом, каждый элемент массива b не обязательно указывает на двадцатиэлементный вектор; один может указывать на два элемента, другой - на пятьдесят, а некоторые и вовсе могут ни на что не указывать.
Наши рассуждения здесь касались целых значений, однако чаще массивы указателей используются для работы со строками символов, различающимися по длине, как это было в функции month_name. Сравните определение массива указателей и соответствующий ему рисунок:
char *name[] = {"Неправильный месяц", "Янв", "Февр", "Март"};
с объявлением и рисунком для двумерного массива:
char aname[][15] = {"Неправ. месяц", "Янв", "Февр", "Март"};
Упражнение 5.9. Перепишите программы day_of_year и month_day, используя вместо индексов указатели.
- 5.1 Указатели и адреса
- 5.2 Указатели и аргументы функций
- 5.3 Указатели и массивы
- 5.4 Адресная арифметика
- 5.5 Символьные указатели функции
- 5.6 Массивы указателей, указатели на указатели
- 5.7 Многомерные массивы
- 5.8 Инициализация массивов указателей
- 5.9 Указатели против многомерных массивов
- 5.10 Аргументы командной строки
- 5.11 Указатели на функции
- 5.12 Сложные объявления
- Глава 5. Указатели и массивы
- 5.8 Инициализация массивов указателей
- «БОМБЫ» ПРОТИВ «ЭНИГМЫ»
- 8.1.4. Сравнение массивов
- 8.1.22. Чередование массивов
- Материнская плата имеет возможность организации RAID-массивов из двух SATA-дисков. Можно ли подключить к ней только один...
- 2.10.5. Безопасность против производительности
- Типы массивов в Delphi
- Очереди на основе массивов
- Противостояние атаке конкурентов
- 11.9. Сериализация массивов и словарей в JSON
- Сортировка массивов