Урок 15. Действия с массивами - 2

Обычно при изучении программирования рассматриваются целые классы задач. Если вы научитесь решать задачи из некоторого класса, вы сможете решать и другие подобные задачи.
Можно выделить классы задач на массивы:
1. Обработка элементов массива.
Типовая задача: Дан массив. Все его элементы увеличить в два раза.
2. Использование сложных условий для отбора элементов.
Типовая задача: Дан массив. Напечатать все элементы, которые попадают в заданный промежуток.
3. Задачи с двумя и более массивами.
Типовая задача: Даны два массива. Получить третий массив, каждый элемент которого равен сумме соответствующих элементов двух массивов.
4. Задачи на изменение порядка следования элементов массива.
Типовая задача - сортировка массива.
5. Задачи на сдвиг массива (изменение количества элементов).
Типовая задача: Дан массив. Удалить из массива максимальный элемент.
6. Задачи на формирование нового массива.
Типовая задача: Дан массив, содержащий положительные и отрицательные элементы. Сформировать массив, состоящий только из положительных элементов.

В качестве примера рассмотрим задачу работы с массивом. Пусть дан одномерный массив, состоящий не более чем из 30 целых элементов. Найти значение элемента, наименее отличающегося от среднего арифметического всех элементов массива (считаем, что он определяется однозначно).

#include
#include
int main( )
{
int a[30], count; // a – массив, count – количество элементов
int i, Nmin; // Рабочие переменные
double s, min; // Рабочие переменные
while(1) // Цикл проверки корректности
{ // количества элементов
printf("\nВведите количество элементов<=30\n");
scanf("%d", &count); // Ввод количества элементов
if (count >0 && count <= 30) break;
}
for( i = 0; i < count; i++) // Цикл ввода элементов массива
{
printf("\nВведите элемент\n");
scanf("%d", &a[i]); // Ввод элемента
}
for( s=0.0, i=0; i < count; i++) // Цикл вычисления суммы элементов массива
s += a[i];
s = s/count; // Среднее арифметическое
min=fabs(s-a[0]); // Находим первую по абсолютной величине разницу
Nmin=0; // и запоминаем номер элемента
for( i=1; i < count; i++) // Находим минимальную разницу для остальных элементов
if(fabs(s-a[i])<min)
{ min=fabs(s-a[i]); // Запоминаем разницу
Nmin=i; } // Запоминаем номер элемента
printf("Элемент имеет значение %d\n", a[Nmin]);
return 0;
}

Примеры алгоритмов на массивы Начало формы Конец формы

Начало формы

Конец формы

 

 

Алгоритмы с массивами

1. Пусть имеется фрагмент программы: int a[] = {0, 1, 2, 3, 4, 5, 6}; int S=0, i; for(i=0; i<7; i++) S+=a[i]; printf("%d", S); Что выполняет этот алгоритм и что будет выведено на экран в результате выполнения этого фрагмента программы?

 

   
2. Пусть имеется фрагмент программы: int a[] = {0, 1, 2, 3, 4, 5, 6}; int S=1, i; for(i=0; i<5; i++) S+=a[i]; printf("%d", S); Что выполняет этот алгоритм и что будет выведено на экран в результате выполнения этого фрагмента программы?

 

   
3. Пусть имеется фрагмент программы: int a[10] = {4,0,1,8,2,3,4,7,5,6}; int b=4, S=0, i; for(i=0; i<10; i++) if(a[i] > b) S+=a[i]; printf("%d", S); Что выполняет этот алгоритм и что будет выведено на экран в результате выполнения этого фрагмента программы?

 



   
4. Пусть имеется фрагмент программы: int a[10] = {4,0,1,8,2,3,4,7,5,6}; int b=a[0], i; for(i=1; i<10; i++) if( a[i]>b ) b=a[i]; printf("%d", b); Что выполняет этот алгоритм и что будет выведено на экран в результате выполнения этого фрагмента программы?

 

   
5. Пусть имеется фрагмент программы: int a[10] = {4,3,1,8,2,3,4,7,5,6}; int S1=a[0], S2=a[9], i; for(i=0; i<10; i++) {if( a[i]>S1 ) S1=a[i]; if( a[i]<S2 ) S2=a[i]; } printf("%d", S2-S1); Что выполняет этот алгоритм и что будет выведено на экран в результате выполнения этого фрагмента программы?

 

   
6. Пусть имеется фрагмент программы: int a[8] = {4,3,1,8,2,3,4,7}; int b[8], i; for(i=0; i<8; i++) b[i]=a[8-i-1]; printf("%d", b[0]+b[1]+b[2]); Что выполняет этот алгоритм и что будет выведено на экран в результате выполнения этого фрагмента программы?

 

   
7. Пусть имеется фрагмент программы: int a[10] = {4,4,4,6,6,1,7,7,7,7}; int M, i; M=a[0]+a[9]; for(i=1; i<5; i++) if(a[i]+a[9-i]>M) M=a[i]+a[9-i]; printf("%d", M); Что выполняет этот алгоритм и что будет выведено на экран в результате выполнения этого фрагмента программы?

 

   
8. Пусть имеется фрагмент программы: int С[8] = {5,6,7,8,1,2,3,4}; int N=8, i; for(i=0; i<N; i++) С[i]=С[i]*2; printf("%d", С[3]+С[4]); Что выполняет этот алгоритм и что будет выведено на экран в результате выполнения этого фрагмента программы?

 

   
9. Пусть имеется фрагмент программы: int a[10] = {4,4,4,6,6,1,7,7,7,7}; int k, i; for(i=0,k=0; i<9; i++) if(a[i]!=a[i+1]) k++; printf("%d", k); Что выполняет этот алгоритм и что будет выведено на экран в результате выполнения этого фрагмента программы?

 

   
10. Пусть имеется фрагмент программы: int c[8] = {5,6,7,8,1,2,3,4}; int N=8, i; for(i=0; i<N-1; i++) c[i+1]=c[i]; printf("%d", c[3]+c[4]); Что выполняет этот алгоритм и что будет выведено на экран в результате выполнения этого фрагмента программы?

 

   
11. Пусть имеется фрагмент программы: int c[5] = {5,6,7,8,1}; int N=5, i,j; for(i=0; i<N-1; i++) for(j=i+1; j<N; j++) printf("%d", c[j]); Что выполняет этот алгоритм и сколько чисел будет выведено на экран в результате выполнения этого фрагмента программы?

 

   
12. Пусть имеется фрагмент программы: int a[10] = {3,8,4,2,8,3,5,5,8,7}; int M,i,k=0; M=a[0]; for(i=1; i<10; i++) if(a[i]>M) M=a[i]; for(i=0; i<10; i++) if(a[i]==M) k++; printf("%d", k); Чему будет равно значение переменной kв результате выполнения этого фрагмента программы?

Урок 16. Двумерные массивы

Двумерные массивы

В соответствии с синтаксисом Си в языке существуют только одномерные массивы, однако элементами одномерного массива могут быть массивы. Поэтому двумерный массив определяется как массив массивов.
Ограничений на количество индексов в языке теоретически нет. Однако чаще всего на практике используются одномерные и двумерные массивы.
Пример определения двумерного массива:

int а[2][3];

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

a[0][0], a[0][1], a[0][2], a[1][0], a[1][1], a[1][2].

 

 

Рок 17. Указатели в языке Си

Что такое указатель

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

Рассмотрим упрощенную схему организации памяти. Память типичной машины подставляет собой последовательность пронумерованных, или проадресованных ячеек, с которыми можно работать по отдельности.
Пусть у нас есть переменная a. Организуем указатель на ячейку a, назовем его pa (как это сделать - скажем позже). В ячейке pa содержится непосредственный машинный адрес переменной a, а стрелка означает, что через указатель можно получить доступ к содержимому ячейки a.
Другими словами, указатель - это ячейка, от которой идет стрелка, указывающая на некую ячейку-переменную.

Сразу встает законный вопрос: откуда берутся эти указатели и как построить эту самую стрелку? Cейчас мы с этим разберемся. Главное сейчас, чтобы осталось представление, что к содержимому переменной a можно добраться и через указатель.

Объявление указателей

Мы помним, что всякое объявление переменной подразумевает выделение ячейки памяти для этой переменной. Поскольку указатель - это тоже ячейка памяти, он должен быть объявлен в программе.
Другое дело, что указатель - не совсем обычная переменная, и в его объявлении есть свои особенности.
Прежде всего, каждая переменная-указатель может указывать на данные только определенного типа: указатель на целочисленную ячейку, на символьную, на вещественную. То есть описанию указателя должно предшествовать ключевое слово int, char или float.
Вторая особенность состоит в том, что непосредственно перед именем переменной-указателя ставится звездочка.
Ну вот, теперь мы знаем достаточно, чтобы объявить, к примеру, два указателя:

int *pа; // объявляем указатель pa на переменную целого типа
char *pb; // pb - указатель на переменную символьного типа

Заметим, что после такого описания сам указатель упоминают уже без звездочки, то есть говорят, что объявлены, в нашем случае, указатели pa и b.
Теперь у нас есть ячейки, которые могут хранить адреса других ячеек.
Но пока что эти указатели еще ни на что не указывают, т.е. в данный момент в ячейках памяти, отведенных под указатель, содержится «мусор»:


Как узнать адрес переменной

Прежде чем указатель «укажет» на какую-либо ячейку, надо сначала узнать адрес этой самой ячейки, а уж потом занести этот адрес в ячейку-указатель.
Получить адрес переменной можно с помощью специальной операции языка Си, которая обозначается значком "&" (амперсанд).
Получение адреса переменой - это унарная операция, то есть такая, которая строится из знака операции – символа &, и одного операнда – имени переменной.
Добавим к нашему описанию еще одно привычное описание переменных:

int а; // объявляем переменную целого типа
char b; // объявляем переменную символьного типа

Теперь операция &a позволит получить адрес ячейки a; операция &b - адрес ячейки b .

Как "построить стрелку"


Сейчас мы ее построим. Адрес переменной a мы знаем, есть и ячейка-указатель, в которую можно занести этот адрес, это рa , осталось выполнить присваивание:

pa=&а;
pb=&b;

Вопросы для самопроверки

1. Чем ячейка-указатель отличается от других переменных?
2. Чем описание указателя отличается от описания переменной?
3. Какая операция позволяет получить адрес переменной?
4. Как связать ячейку-указатель с переменной?

 









Последнее изменение этой страницы: 2016-04-07; Нарушение авторского права страницы

infopedia.su не принадлежат авторские права, размещенных материалов. Все права принадлежать их авторам. Обратная связь