МИНИСТЕРСТВО ОБРАЗОВАНИЯ РОССИЙСКОЙ ФЕДЕРАЦИИ НИЖЕГОРОДСКИЙ ГОСУДАРСТВЕННЫЙ УНИВЕРСИТЕТ им. Н.И.ЛОБАЧЕВСКОГО МЕХАНИКО-МАТЕМАТИЧЕСКИЙ ФАКУЛЬТЕТ Кафедра теоретической механики Кафедра численного моделирования физико-механических процессов Сборник заданий по вычислительному практикуму на языке Си. Методическое пособие НИЖНИЙ НОВГОРОД 2002 УДК 519.682 Сборник заданий по вычислительному практикуму на языке Си. Методическое пособие / Сост. В.В. Денисов, М.В. Маркина Т.А. Сабаева, О.Г. Савихин. - Н.Новгород: изд-во ННГУ, 2002. - 56 с. Методическое пособие предназначено для студентов механикоматематического факультета и других факультетов ННГУ и призвано оказать помощь в практическом использовании персональных компьютеров в учебном процессе. Составители: зав. лаб. В.В. Денисов к.ф.-м.н., доцент М.В. Маркина к.ф.-м.н , доцент Т.А. Сабаева к.т.н., доцент О.Г. Савихин (Глава 1,2), (Глава 3,7), (Глава 8), (Глава 3,4,5,6) Рецензент: Нижегородский государственный университет им. Н.И. Лобачевского, 2002 2 ОГЛАВЛЕНИЕ 1. ВЫЧИСЛЕНИЕ ЗНАЧЕНИЙ ФУНКЦИИ.............................................. 4 2. ВЫДЕЛЕНИЕ ОБЛАСТЕЙ ...................................................................... 7 3. СУММИРОВАНИЕ РЯДОВ .................................................................. 15 4. ПОЗИЦИОННАЯ ЗАПИСЬ ЧИСЛА ..................................................... 18 5. ДЕЛИТЕЛИ ЦЕЛОГО ЧИСЛА............................................................. 23 6. ПРЕОБРАЗОВАНИЕ И ПОСТРОЕНИЕ ОДНОМЕРНЫХ МАССИВОВ................................................................................................ 27 6.1 ЛИНЕЙНЫЙ ПОИСК В МАССИВЕ .............................................. 27 6.2 ПОСТРОЕНИЕ МАССИВА БЕЗ ПОВТОРЕНИЙ ......................... 29 7. МАКСИМАЛЬНЫЙ И МИНИМАЛЬНЫЙ ЭЛЕМЕНТЫ МАССИВА.СОРТИРОВКА ....................................................................... 31 8. ОБРАБОТКА ПОСЛЕДОВАТЕЛЬНОСТЕЙ СИМВОЛОВ ................ 39 9. ПРЕОБРАЗОВАНИЕ И ПОСТРОЕНИЕ МАТРИЦ ............................. 41 ЛИТЕРАТУРА ............................................................................................ 55 3 1. ВЫЧИСЛЕНИЕ ЗНАЧЕНИЙ ФУНКЦИИ y n lg( 26 x 2 ) Пример 1. Вычислить значение функции . Значение переменной x и параметра n вводить с клавиатуры (n – целое). #include <stdio.h> #include <math.h> main() {int n; float x; char yn,temp; do { printf("введите n-целое................"); scanf("%i",&n); printf("введите x-десятичное..........."); scanf("%g",&x); if (fabs(x)<5) printf(".........y(%g,%i)=%g\n",x,n,exp(log(log10(26-x*x))/n)); else if ((fabs(x)>5)&&(fabs(x)<sqrt(26))&&(n % 2)) printf(".........y(%g,%i)=%g\n",x,n,-exp(log(-log10(26-x*x))/n)); else if ((fabs(x)==5)&&(n>0)) printf(".........y(%g,%i)=%g\n",x,n,0/n); else printf("Функция не определена\n"); printf("Продолжить работу-y, закончить-n\n"); temp=getchar(); yn=getchar(); temp=getchar(); } while ((yn!='n')&&(yn!='N')); } 4 Тест: n 3 5 2 4 5 x -4.8 5.05 -4 6 5 y 0.912448 -0.787677 1 решений нет 0 УПРАЖНЕНИЯ Вычислить значение функции y от x. Значение переменной x и параметров a и b вводить с клавиатуры (Параметр a вещественного типа , параметр b целочисленный, справа от функции даны значения для теста программы): 1. y ln(5 ax) b ; при x=3,5; a=0.2; -1,5 b=2; 3 2. y ln(cos ax ) ; при x=0.3; a=2,1; 9,8 b=1; 6; 3. y b sin(b ax) ; при x=1.03; a=2,5; 0,3; b=2; 3 b 3 4. y logax (3 bx) ; при x=0.3; 5. y ( x 2 sin ax)b ; при x=1.3; a=0,2; -1,2 a=0,2; 3,1; b=6; -1 b=2; 3; 6. y (ax)b /2 3 ; a=1,2; -1,5; b=2; 3; a=1,2; 4,5; a=-4; -5.2; b=4; 1; b=6; 1 при x=2.3; a=-1.2; 0,3 b=2; 3 при x=-1.3; a=-2,2; 1,1 b=2; 3 при x=2.3; b 4 7. y ln (ax b) ; при x=1.03; 8. y logb3 / 3 (5 ax 3 ) ; при x=1.03; b 2 2 9. y (b ax ) ; b 5 10. y ( x 3 ax ) ; 11. y log3 b (9 x ax) ; при x=1.03; a=-1,2; 2,3 b=3; 2 5 12. y log5 (5 ax)b ; при x=3,5; a=0.2; -1,5 b=2; 3 a=2,1; 9,8 b=1; 6; 14. y b sin(b ax 2 ) ; при x=1.03; a=2,5; 0,3; b=2; 3 15. y logax (3 bx) 3 ; при x=0.3; 16. y ( x 2 sin ax)b / 2 ; при x=1.3; a=0,2; -1,2 a=0,2; 3,1; b=6; -1 b=2; 3; 17. y (ax )b / 2 3 ; при x=2.3; a=1,2; -1,5; b=2; 3; b 3 13. y (cos ax ) ; при x=0.3; 2 b 2 18. y ln (ax b / 2) ;при x=1.03; a=1,2; 4,5; b=2; 3; 19. y lnb / 3 (5 ax 3 ) ; при x=1.03; a=-4; -5.2; b=6; 1 2 b 2 2 20. y (b ax ) 1 ; при x=2.3; a=-1.2; 0,3 b=2; 3 21. y b ( x 2 ax ) ; a=-2,2; 1,1 b=2; 3 22. y log 3 b (1 ax ) ; при x=1.03; a=-1,2; 2,3 b=3; 2 23. y ( x 3 sin ax)b / 4 ; при x=1.3; a=0,2; 3,1; b=4; 5; 24. y (ax )b / 4 3 ; при x=2.3; a=1,2 ;-1,5; b=4; 5; a=1,2; 4,5; b=2; 3; при x=-1.3; 3 b 2 25. y log3 (ax 1) ; при x=1.03; 6 2. ВЫДЕЛЕНИЕ ОБЛАСТЕЙ Пример. Определить принадлежность точки с координатами x,y заштрихованной части плоскости: #include <stdio.h> #include <math.h> #define sq(t) ((t)*(t)) main() {float x,y; char yn,temp; do { printf("введите координату x..............."); scanf("%g",&x); printf("введите координату y..............."); scanf("%g",&y); if (!(x==0)&&(((sq(x-1)+sq(y-1)<=1)&&((y>=x)&&(y>=1/x)|| (y<=x)&&(y<=1/x)))||((sq(x-1)+sq(y-1)>=1)&&((y>=x)&& (y<=1/x)&&(x<0)||(y<=x)&&(y>=1/x)&&(x>0))))) printf("....принадлежит....\n"); else printf("...не принадлежит....\n"); printf("Продолжить работу-y, закончить-n\n"); temp=getchar(); yn=getchar(); temp=getchar(); } while ((yn!='n')&&(yn!='N')); } 7 Тест: x 1 1 1 4 -5 -2 -1 y 0.5 1.5 3 2 -1 -0.01 1 результат да да нет да да нет нет УПРАЖНЕНИЯ Определить принадлежность точки с координатами x,y заштрихованной части плоскости: 1. 2. 8 3. 5. 4. 6. 9 7. 9. 8. 10. 10 11. 13. 12. 14. 11 15. 17. 16. 18. 12 19. 21. 20. 22. 13 23. 24. 25. 14 3. СУММИРОВАНИЕ РЯДОВ Пример. Вычисление бесконечной суммы S= 1n n 0 x 2n для (2n)! f ( x) cos( x). с заданной точностью . Счи- тается , что заданная точность достигается ,если вычислена сумма нескольких первых слагаемых и очередное слагаемое оказалось по модулю меньше, чем Реккурентная формула , связывающая значения последующего слагаемого с предыдущим имеет вид: у n 2 ( 1) у n x2 n(n 1) Для выхода из цикла суммирования проводится сравнение значения очередного слагаемого и . Первое слагаемое, оказавшееся меньше чем , в сумму не добавляется и на этом вычисления прекращаются. #include <iostream.h> main() { long double eps,s,y,x; int n; n=0; eps=1.e-5; s=0; y=1.; cin>>x; while(fabs(y)>eps) { s=s+y; n=n+2; y=(-1)*y*x*x/(n*(n-1)); } cout<<s<<" "<<n-2; } 15 УПРАЖНЕНИЯ Выполнить следующие вычисления: а) задавая x и n (число членов суммы ряда), найти сумму S и s f (x) ; б) задавая x и n (число членов суммы ряда), найти сумму S в порядке убывания индекса до нуля; в) задавая x и 0 , найти сумму S и число членов суммы n. Суммирование выполнять до тех пор, пока не выполнится условие: s f ( x) 0 1. 1 n(n 1) n 0 2. 1 1 2 n 0 1 n 0 5. n 1 , 1 n n 0 7. 8. 1 1 n! , f ( x ) 1 / 2. f ( x ) 2 / 3. f ( x ) e. , 1 2n 1 n 0 1n 1 12 , n n 0 n 1 , f ( x ) 2. 1 2n n! n 0 6. , n 4. f ( x ) 1. (2n 1)( 2n 1) n 0 3. , f ( x ) 1 / e. , f ( x ) / 4. f ( x ) 2 / 12. 16 9. 1 n 1 n 0 1 n4 f ( x ) 7 4 / 720. , x 2n , f ( x ) cos( x ). (2n)! n 0 x 2 n 1 n 11. 1 , f ( x ) sin( x ). (2n 1)! n 0 10. 1n 12. x 2 n 1 n 0 ( 2n 1)! f ( x ) sh( x ). , x 2n n 0 ( 2n )! x 2 n 1 14. n 0 ( 2n 1) f ( x ) ch( x ). , 13. x 2 n 1 15. n 0 ( 2n 1) , f ( x ) arth( x ). , f ( x ) arcth( x ). x 2 n 1 , (2n 1) n 0 (2n 1)!! x 2 n 1 17. n 0 ( 2n )!! ( 2n 1) 16. 1n 18. n 1 19. n 1 20. ( x 1) n nx n f ( x ) arcsin( x ). , f ( x ) ln( x ). , xn n , x 1n 1 n 1 f ( x ) arctg ( x ). f ( x ) ln( 1 x ). n n , f ( x ) ln( 1 x ). 17 21. n 0 22. n 0 23. n 0 24. xn n! , ( x ln a ) n n! 1 ( n 1) x n n f ( x) a x . , xn n f ( x ) ln( x ) / 2. f ( x) e x . , 1 n 0 25. ( x 1) 2 n 1 (2n 1)( x 1) 2 n 1 , f ( x ) 1 /(1 x ). , f ( x ) 1 /(1 x ) 2 . n 0 4. ПОЗИЦИОННАЯ ЗАПИСЬ ЧИСЛА Пример 1. Найти количество цифр в числе и поменять их порядок на обратный. Для решения задачи используем позиционную запись числа в десятичной системе счисления: n=ak-110k-1+ ak-210k-2+ ...+a1101+a0. Остаток от деления n на 10 даст a0. Разделим n на 10 , а результат обозначим через n1 : n1= ak-110k-2+ ak-210k-3+ ...+a2101+a1. Остаток от деления n1 на 10 даст a1. Повторяя операцию деления до тех пор , пока не результат не будет равен 0, найдем все цифры числа n. При этом число шагов деления совпадает с количеством цифр в числе. Образуя сумму по реккурентной формуле mk=mk-110+ ak-1, получим значение числа с обратным порядком цифр. #include <iostream.h> #include<math.h> main() { int n,m,k; m=0; 18 k=0; cin>>n; while(n>0) { m=10*m+n%10; n=n/10; k=k+1; } cout<<"число цифр :"<<k<<endl; cout<<"палиндром :"<<m<<endl; Пример 2. Дано натуральное число n . Выбросить из записи числа n цифры 0 и 5,оставив прежним порядок остальных цифр. Процесс нахождения остатков с последующим делением исходного числа на 10 позволяет найти цифры исходного числа в обратном порядке. При образовании суммы числа с удаленными цифрами необходимо цифры исходного числа умножать на 10 в соответствующей степени. Возведение в степень реализуетя с помощью алгоритма умножения на 10 в основном цикле. #include <iostream.h> #include<math.h> main() { long int n,m,k,l; m=0; k=1; cin>>n; while(n>0) { l=n%10; if(l!=5 && l!=9) { m=m+k*l; k=k*10; } n=n/10; } cout<<m<<endl; } 19 Пример 3. Найти все трехзначные десятичные числа, сумма цифр которых равна заданному натуральному числу Решение содержит два вложенных цикла по числу единиц и числу десятков. Число сотен вычисляется по заданной сумме цифр. #include <iostream.h> main() {int n; int i,j,k; do cin>>n; while(n<=0 && n>27); for(i=0;i<=9;i++) for(j=0;j<=9;j++) { k=n-i-j; if(k>=1 && k<=9) cout<<i+j*10+k*100<<endl; } } УПРАЖНЕНИЯ 1. Определить количество натуральных трехзначных чисел, сумма цифр которых равна заданному числу N. . 2. Среди четырехзначных чисел выбрать те, у которых все четыре цифры различны. Найти количество четных цифр заданного натурального числа N. Найти все симметричные натуральные числа ( палиндромы ) из интервала от К до L. Для данного натурального числа N определить: содержит ли число одинаковые цифры и их количество. Найти все натуральные числа , не превосходящие заданного N, и делящиеся на каждую из своих цифр Найти все натуральные числа , не превосходящие заданного N, десятичная запись которых есть строго возрастающая или стро- 3. 4. 5. 6. 7. 20 8. го убывающая последовательность цифр. Найти все пары двухзначных натуральных чисел М и Н таких, что значение произведения М*Н не изменится ,если поменять местами цифры каждого из сомножителей(такой парой будет , например, 38 и 83). 9. Определить сколько раз данная цифра К встречается в целом числе N. 10. Среди двузначных чисел найти те, сумма квадратов цифр которых делится на 13. 11. Даны натуральные числа N. М. Получить все натуральные числа меньшие N. квадрат суммы цифр которых равен М. Написать программу, которая находит все четырехзначные числа КLMN. где К, L, М, N - различные цифры, для которых выполняется соотношение: КL - МN =К+L+М+N Написать программу поиска двузначных чисел, обладающих следующим свойством: если к сумме цифр числа прибавить квадрат этой суммы, то получится снова данное число. Некоторое число оканчивается на 2. Если же эту его последнюю цифру переставить на первое место, то число удвоится. Найти это число. 12. 13. 14. Определить пятизначное число А, удовлетворяющее следующему условию. Образуем два шестизначных числа приписав единицы впереди числа А и в конце его: [1] [А]; [А] [I]. Второе шестизначное число должно быть втрое больше первого:[A][1]/[1][A]=3 15. Квадраты некоторых трехзначных чисел оканчиваются тремя цифрами, которые как раз и составляют исходные числа. Написать программу поиска таких чисел. В трехзначном числе зачеркнули первую цифру слева. Когда полученное двузначное число умножили на 7, то получили исходное число. Найти исходное число. Найти все трехзначные числа, которые при увеличении на 1 делятся на 2, при увеличении на 2 делятся на 3, при увеличении на 3 делятся на 4, а при увеличении на 4 делятся на 5. 16. 17. 21 18. 19. 20. 21. 22. 23. 24. 25. 26. 27. Найти все трехзначные числа, которые при делении на 2 дают остаток 1, при делении на 3 - остаток 2, при делении на 4 остаток 3, а само число делится на 5. Найти все двузначные числа, которые при умножении на 2 заканчивается на 8, а при умножении на 3 - на 4. Сумма цифр трехзначного числа кратна 7, само число также делится на 7. Найти все такие числа. Дано четырехзначное число N. Выбросить из записи числа N цифры 0 и 5, оставив прежним порядок остальных цифр. Например, из числа 1509 должно получится 19. . Натуральное число из N цифр является числом Армстронга, если сумма его цифр, возведенных в N-ю степень, равна самому числу ( например, 153 = I3 + 53 + З3). Получить все числа Армстронга, состоящие из трех и четырех цифр. Определить число счастливых билетов в рулоне с номерами билетов от 000000 до 999999. Счастливым считается билет, для которого выполняется условие: N1+N2+N3=N4+N5+N6. Переставить цифры данного натурального числа таким образом, чтобы образовалось наименьшее число, записанное этими цифрами. Если мы сложим все цифры какого-либо числа, затем все цифры найденной суммы и будем повторять этот процесс, мы, наконец, получим однозначное число ( цифру ), называемое цифровым корнем данного числа. Например, цифровой корень числа 34697 равен 2 ( 3+4+6+9+7=29 ; 2+9=11 ; 1+1=2 ). Составить программу для нахождения цифрового корня натурального числа N Найти все автоморфные числа из промежутка от К до L. Автоморфным называется число, квадрат которого заканчивается им самим. Например, автоморфным является число 6, так как его квадрат 36 заканчивается на 6, или число 25 - его квадрат 625. Рассмотрим некоторое натуральное число. Если это не палиндром, то изменим порядок его цифр на обратный и сложим исходное число с получившимся. Если сумма не палиндром, то над ней повторяется, то же действие и т.д., пока не получится палиндром. Даны натуральные числа К, М, Ь ( К < 1.). Прове- 22 рить, верно, ли, что для любого натурального числа из диапазона от К до Ь процесс завершается не позднее, чем после М таких действий Найти все трехзначные числа, удовлетворяющие следующим условиям: 29. • любые две цифры числа различны ; 30. • число равно среднему арифметическому всех трехзначных чисел (включая данное), состоящих из тех же цифр. 31. Напечатать k- ю цифру последовательности 32. а) 12345678910111213…, в которой выписаны подряд все натуральные числа; 33. б) 110100100010000100000…, в которой выписаны подряд степени 10 ; 34. в)149162536…, …, в которой выписаны подряд квадраты всех натуральных чисел ; г)1123581321…, в которой выписаны подряд все числа Фибоначи 28. 5. ДЕЛИТЕЛИ ЦЕЛОГО ЧИСЛА Пример 1. Найти все делители неотрицательного целого числа n. Вариант 1.Самый простой способ решения – это проверить по очереди делимость числа n на каждое из чисел 1,2,3, ... , n. Число операций можно сократить, доказав, что в интервале [n/2+1,n-1] делителей числа n нет. #include <iostream.h> main() { int n,d; cin>>n; for (d=1;d<=n/2;d++) if(n%d==0) cout<<d<<endl; } Вариант 2. Для нахождения делителей числа n , достаточно обнаружить делители не превышающие значения квадратного корня из числа n. Все остальные делители получаются в результате деления числа n на найденные делители. 23 #include <iostream.h> main() { int n,d; cin>>n; for (d=1;d*d<n;d++) if(n%d==0) cout<<d<<", "<<n/d<<endl; if(d*d==n) cout<<d<<endl; } Пример 2. Найти наибольший делитель двух неотрицательных целых чисел. Решение основано на алгоритме Евклида, многократно использующим целочисленную операцию деления с остатком: n=q*m+r0, m=q0*r0+r1, r0=q1*r1+r2 .......................... rk-1=qk*rk+rk+1, ........... rj-1=qj*rj, где rj – наибольший общий делитель. #include <iostream.h> main() { long int n,m,r,tmp; cin>>n>>m; if(m>n) { tmp=m; m=n; n=tmp;} while(m>0) { r=n%m; n=m; m=r; } cout<<n; } 24 Пример 3. Найти все простые числа , меньшие заданного натурального числа n. Вариант 1. Для решения задачи необходимо проверить имеют ли числа из заданного интервала делители, не превышающие значения квадратного корня из числа n.. Четные числа можно не рассматривать, поскольку они делятся на два. #include <iostream.h> main() { int d,k,n; cin>>n; cout<<1<<endl<<2<<endl<<3<<endl; k=5; while (k<=n) { for (d=2;d*d<=k && k%d!=0;d++) ; if(d*d>k) cout<<k<<endl; k=k+2; } } УПРАЖНЕНИЯ 1. Дано натуральное число N. Получить все его натуральные делители. 2. Найти количество делителей натурального числа N. Сколько из них четных? 3. Найти сумму нечетных делителей натурального числа N. 4. Найти все натуральные числа из интервала от 1 до 200, у которых количество делителей равно N. 5. Найти сумму целых чисел из промежутка от 1 до 200, у которых ровно 5 делителей Найти все целые числа из промежутка от 100 до 300, у которых сумма делителей равна К. 6. 25 7. 8. Найти натуральное число лежащее в диапазоне от 1 до 10000 с максимальной суммой делителей. Найти все натуральные числа из промежутка от К до L, у которых количество делителей превышает заданное число М. 9. 10. Найти сумму четных делителей натурального числа N. Найти все натуральные числа из промежутка от 1 до 200, у которых сумма четных делителей равна N. 11. Найти количество делителей натурального числа N. больших К. 12. Найти все целые корни уравнения ax3+bx2+cx+d=0 , где a,b,c,d – целые числа. 13. Даны целые числа p и q Получить все делители числа q , взаимно простые с p 14. Дано целое число n .Получить все простые делители этого числа 15. На интервале (1000, 9999) найти все простые числа, каждое из которых обладает тем свойством, что сумма первой и второй цифр в записи этого числа равна сумме третьей и четвертой цифр. Даны натуральные числа К, Ь (К < Ь). Получить все простые числа I, удовлетворяющие неравенству: К < I < Ь, используя решето Эратосфена. Дано натуральное число N > 2. Составить программу разложения этого числа на простые множители. Каждый простой множитель L должен быть выведен k раз, где k-натуральное число, такое, что N делится на Lk и не делится на Lk+1; Дано натуральное число N > 2. Составить программу разложения этого числа на простые множители. Каждый простой множитель должен быть выведен один раз 16. 17. 18. 19. Найти наибольший общий делитель ( НОД ) трех чисел, используя соотношение НОД(К,L,М) = НОД(НОД( К, L ), M) и алгоритм Евклида 20. Даны натуральные числа М, N. Получить все кратные им числа, меньшие МхN 26 21. Для натуральных чисел К и L определить наименьшее общее кратное (НОК), используя соотношение: НОД (K,L)=KL/ НОД (K,L) Даны M ( М > 2 ) натуральных чисел: N1,N2, ..., Nм. Вычислить НОД (N1,N2, ..., Nм ), используя соотношение НОД(N1,N2, ..., Nм)= НОД(НОД(N1,N2, ..., Nм-1 ), Nм ) и алгоритм Евклида. . 22. Найти все простые несократимые дроби, заключенные между 0 и 1, знаменатели которых не превышают 7 (дробь задается двумя натуральными числами - числителем и знаменателем ) . Составить программу сложения двух дробей. Результат сложения - несократимая дробь Составить программу для нахождения всех совершенных чисел, меньших заданного числа N. Совершенным называется число, равное сумме всех своих положительных делителей ( включая единицу, но исключая само число ). Например, 28 совершенное число, т.к. 28 = 1 + 2 + 4 + 7 + 14.. 23. 24. 25. Даны натуральные числа N. М. Найти все пары натуральных дружественных чисел, лежащих в диапазоне от N до М. Два числа называются дружественными, если каждое из них равно сумме всех делителей другого ( само число в качестве делителя не рассматривается). . 6. ПРЕОБРАЗОВАНИЕ И ПОСТРОЕНИЕ ОДНОМЕРНЫХ МАССИВОВ 6.1 Линейный поиск в массиве Линейный поиск заключается в последовательном просмотре всех элементов массива до обнаружения первого элемента, удовлетворяющего заданному условию. В этом случае проверки прекращаются и организуется выход из цикла. Выход из цикла осуществляется с помощью включения условия отбора в условие окончания цикла. 27 Пример 1. Найти первый положительный элемент массива. #include <iostream.h> main() { const int n=5; int m[n]={-1,-2,-1,3,-5}; int I; for (I=0;I<n && m[I]<=0 ;I++) ; if(I>=n) cout<<”no”; else cout<<m[I]; } Пример 2. Найти все простые числа , меньшие заданного натурального числа n. Вариант 2. Для ускорения вычислений можно использовать таблицу для уже найденных простых чисел и проверять делимость очередного кандидата только на числа из этой таблицы. Таблица формируется в процессе поиска с помощью размещения каждого следующего простого числа в первом свободном месте массива. Для этого используется вспомогательная переменная , которая хранит индекс этого элемента. #include <iostream.h> main() { long d,k,n,m,i; long p[100]; cin>>n; k=5; m=0; p[0]=3; cout<<1<<endl<<2<<endl<<3<<endl; while (k<=n) { for (i=0;i<=m && p[i]*p[i]<=k && k%p[i]!=0;i++) ; if(i>m || p[i]*p[i]>k) { cout<<k<<endl; 28 m=m+1; p[m]=k; } k=k+2; } } 6.2 Построение массива без повторений Построение массива без повторений из массива, в который одни и те же элементы могут входить многократно, состоит в комбинировании алгоритма поиска заданного элемента и алгоритма построения массива вставкой нового элемента в конец. Суть алгоритма заключается в следующем. Установим количество элементов формируемого массива без повторений в ноль. Затем будем брать по очереди все элементы исходного массива с повторениями и искать каждый из них в массиве без повторений. Если исходный элемент уже есть в массиве без повторений, ничего не делаем и переходим к следующему элементу в массиве с повторениями. Если искомый элемент отсутствует в массиве без повторений, добавляем его в конец массива и переходим к следующему шагу в цикле просмотра массива с повторениями. #include <iostream.h> #include <iomanip.h> #include <math.h> main() { const int n=10; int i,j,k,tmp,rez[10],m[n]={2,3,2,5,9,-1,9,3,2,2}; i=-1; for(j=0;j<n;j++) { for(k=0;k<=i && rez[k]!=m[j];k++) ; if(k>i) { i=i+1; rez[i]=m[j]; } } for(j=0;j<=i;j++) cout<<setw(3)<<rez[j]; } 29 УПРАЖНЕНИЯ Даны два массива целых чисел a и b , каждый из которых не содержит повторяющихся элементов 1. Построить пересечение массивов a и b 2. Построить объединение массивов a и b 3. Получить все элементы массивов а, которые не входят в массив b. 4. Получить все элементы массивов a и b, которые не входят в них одновременно. 5. Получить все элементы, содержащиеся хотя бы в одном из массивов a и b (если число есть в обоих массивах, в новом оно должно появиться только один раз) 6. Верно ли, что все элементы массива а входят в массив b 7. Верно ли, что все элементы массива а входят в массив b и при этом а[1] встречается в массиве b не позднее , чем а[2], а[2] встречается в массиве b не позднее , чем а[3] и т.д. 8. Верно ли, что два массива, которые могут содержать повторяющиеся элементы, отличаются не более чем порядком их следования Дан массив целых чисел a, который может содержать повторяющиеся элементы 9. Получить все числа, которые входят в массив по одному разу 10. Получить все числа, взятые по одному из каждой группы равных элементов 11. Найти число различных элементов массива 12. Выяснить, сколько чисел входят в массив по одному разу 13. Выяснить, сколько чисел входят в массив более чем по одному разу 14. Выяснить, имеется ли массиве хотя бы одна пара совпадающих чисел 15. Найти число повторяющееся в массиве максимальное количество раз 16. Найти число вхождений каждого элемента массива 30 17. Удалить из массива а все отрицательные элементы 18. Удалить из массива а все элементы , значения которых совпадают с максимальным 19. Переставить все элементы массива так, чтобы сначала расположились все ее неотрицательные элементы, а затем все отрицательные. Порядок как среди неотрицательных элементов, так и среди отрицательных должен быть сохранен прежним 20. Циклически сдвинуть на k позиций влево все элементы массива 21. Расположить все элементы массива в обратном порядке 22. Преобразовать массив по следующему правилу : а[k]=max a[j] при 0<=j<=k 23. Найти упорядоченную по возрастанию последовательность подряд расположенных элементов массива максимальной длины 24. Найти симметричную последовательность подряд расположенных элементов массива максимальной длины 25. Найти последовательность подряд расположенных неповторяющихся элементов массива максимальной длины 7. МАКСИМАЛЬНЫЙ И МИНИМАЛЬНЫЙ ЭЛЕМЕНТЫ МАССИВА.СОРТИРОВКА Пример 1. Поменять местами максимальный и минимальный элементы массива Алгоритм поиска сводится к определению переменной , в которой будет храниться значение максимума (минимума) и последующем сравнением ее величины со всеми элементами массива. В качестве начального значения можно использовать первый элемент массива. Для решения задачи необходимо знать где находятся максимальный и минимальный элементы массива. Для этого вводятся две вспомогательные переменные, в которые заносятся индексы искомых элементов. 31 #include <iostream.h> #include <iomanip.h> #include <math.h> main() { const int n=10; int i,j,k,max,min,tmp,m[n]={6,3,1,5,9,-1,-9}; max=m[0]; min=m[0]; for(i=0;i<n;i++) { if(m[i]>max) { max=m[i]; j=i; } if(m[i]<min) { min=m[i]; k=i; } } tmp=m[k]; m[k]=m[j]; m[j]=tmp; cout<<min<<max; } Пример 2. Поиск максимального и минимального элементов в массиве в сочетании с условием отбора. Поскольку необходим поиск min и max среди элементов массива, удовлетворяющих заданному условию, то величина первого такого элемента заранее неизвестна. Начальное значение переменной, в которой хранится min (max) должно быть заведомо большим (меньшим) , чем любой из элементов массива, удовлетворяющих заданному условию. В качестве начального значения может служить максимально возможная величина, представимая в ЭВМ для типа данных элементов массива. Эти значения имеют именованные константы, определеные в библиотеках limits.h для целых типов и float.h для вещественных типов. 32 Программа ,печатающая значения именованных констант #include <iostream.h> #include<iomanip.h> #include<limits.h> #include<float.h> main() {cout<<"LONG_MIN "<<LONG_MIN<<"LONG_MAX "<<LONG_MAX<<endl; cout<<"FLT_MIN "<<FLT_MIN<<"FLT_MAX "<<FLT_MAX<<endl; cout<<"DBL_MIN "<<DBL_MIN<<"DBL_MAX "<<DBL_MAX<<endl; cout<<"LDBL_MIN "<<LDBL_MIN<<"LDBL_MAX "<<LDBL_MAX<<endl; cout<<"FLT_DIG "<<FLT_DIG<<"FLT_EPSILON "<<FLT_EPSILON<<endl; Программа поиска минимального положительного элемента в массиве #include <iostream.h> #include <iomanip.h> #include <math.h> #include <float.h> main() { const int n=10; double i,j,k,max,min,tmp,m[n]={6.,3.,1.,5.,9.,-1.,-9.}; min=DBL_MAX; for(i=0;i<n;i++) { if(m[i]>0 && m[i]<min) min=m[i]; } cout<<min; } 33 Пример 3. Сортировка массива методом “пузырька” Вариант 1. Последовательным просмотром элементов массива m c индексом i от 0 до n-1 найдем наименьшее i, такое, что m[i]>m[i+1]. Поменяем местами m[i] и m[i+1] и возобновим просмотр с элемента m[i+1] и т. д. В результате самое большое число передвинется на последнее место. Следующие просмотры необходимо начинать с элемента с индексом 0, уменьшив на 1 количество просматриваемых элементов. Массив будет упорядочен после просмотра в котором участвовали первый и второй элементы. #include <iostream.h> #include <iomanip.h> #include <math.h> main() {int i,j,n,k,max,min,tmp,m[10]={6,3,1,5,9,-1,-9,7,2,0}; n=10; for(i=0;i<n-1;i++) for(j=0;j<n-1-i;j++) if(m[j]>m[j+1]) { tmp=m[j]; m[j]=m[j+1]; m[j+1]=tmp; } for(i=0;i<n;i++) cout<<setw(3)<<m[i]; } Вариант 2. Недостатком алгоритма первого варианта является независимость количества действий от степени упорядоченности элементов массива . Даже для полностью упорядоченного массива количество выполненных операций будет пропорционально n2. метод сортировки можно улучшить, использовав в качестве признака окончания сортировки значение вспомогательной переменной. Вспомогательная переменная будет иметь отличную от нуля величину, если в результате просмотра всего массива произошел обмен хотя бы одной пары элементов. 34 #include <iostream.h> #include <iomanip.h> #include <math.h> main() { const int n=10; int i,j,k,tmp,m[n]={6,3,1,5,9,-1,-9,7,2,0}; i=1; while(i>0) { i=0; for(j=0;j<n-1;j++) if(m[j]>m[j+1]) { tmp=m[j]; m[j]=m[j+1]; m[j+1]=tmp; i=1; } } for(i=0;i<n;i++) cout<<setw(3)<<m[i]; } Пример 4. Бинарный поиск в упорядоченном массиве При бинарном поиске искомое значение х сначала сравнивается с элементом в середтне массива. Если х меньше, чем это значение, то областью поиска становится верхняя половина массива, в противном случае – нижняя. Процесс половинного деления продолжается до тех пор ,пока либо будет найдено значение, совпадающее с х, либо диапазон поиска станет пустым. Поскольку на каждом шаге диапазон поиска уменьшается в два раза ,то общее количество необходимых операций будет пропорционально log2n, где n – размерность массива. 35 #include<iostream.h> #include<iomanip.h> #include<conio.h> void main() { clrscr(); const int n=9; float m[n]={1,2,3,4,5,6,7,8,9}; float x; int end=1; cin>>x; int i=0,j=n,k; while (j>i && end!=0) { k=(i+j)/2; if(m[k]>x) j=k; else if( m[k]<x) i=k; else end=0; } if(end==0) cout<<k; else cout<<"no"<<endl; } УПРАЖНЕНИЯ 1. 2. 3. 4. 5. 6. Даны пять различных целых чисел. Упорядочить их по возрастанию, используя не более семи сравнений. Определить упорядочены ли элементы массива Заданы координаты n точек на плоскости. Найти прямоугольник , объемлющий все эти точки. Поменять местами максимальный отрицательный и минимальный положительный элементы массива Вывести на экран элементы массива целых чисел, имеющих максимальное количество делителей. Вывести на экран элементы массива целых чисел, имеющих максимальную сумму цифр. 36 7. 8. 9. 10. 11. 12. 13. 14. 15. 16. 17. 18. Вывести на экран в порядке возрастания четные элементы массива Вывести на экран различные элементы массива целых чисел в порядке возрастания их числа повторения. Вывести на экран элементы массива целых чисел в порядке возрастания их числа делителей. Вывести на экран элементы массива целых чисел в порядке возрастания их суммы цифр. Найти методом бинарного поиска в упорядоченном массиве местонахождения всех чисел от 0 до 9. Заданы два одномерных упорядоченных массива а и b. Найти методом бинарного поиска все элементы массива а, которые не входят в массив b. Заданы два одномерных упорядоченных массива а и b. Вывести на экран различные элементы массива а в порядке появления их в массиве b. Заданы два одномерных упорядоченных массива а и b. Вывести на экран различные элементы массива а в порядке обратном появлению их в массиве b. Заданы два одномерных упорядоченных массива а и b. Получить новый массив, состоящий из чисел массивов а и b без повторений, упорядоченный по возрастанию. Заданы два одномерных упорядоченных массива размерностью m и n соответственно. Образовать из этих элементов упорядоченный массив размерностью m+n Упорядочить массив, используя алгоритм сортировки слиянием упорядоченных групп элементов массива. Вначале весь массив рассматривается как совокупность упорядоченных групп по одному элементу в каждом. Слиянием соседних групп получаем упорядоченные группы, каждая из которых содержит два элемента. Далее упорядоченные группы укрупняются тем же способом и т.д. Алгоритм предполагает использование вспомогательного массива. Упорядочить массив, используя алгоритм сортировки выбором: отыскивается максимальный элемент и переносится в конец массива; затем этот метод применяется ко всем элементам , 37 19. 20. 21. 22. 23. 24. 25. кроме последнего (он уже находится на своем окончательном месте), и т.д. Упорядочить массив, используя алгоритм сортировки вставками: пусть первые n элементов уже упорядочены; берется (n+1)й элемент и с помощью последовательного просмотра размещается среди первых n элементов так, чтобы упорядоченными оказались уже (n+1) первых элементов, и т.д. Упорядочить массив, используя алгоритм сортировки бинарными вставками , в котором место размещения элемента в упорядоченном отрезке массива определяется методом бинарного поиска. Дана ведомость зарплаты сотрудников, в которой указаны табельный номер сотрудников и зарплата каждого. Вывести на экран список табельных номеров сотрудников в порядке увеличения их зарплаты. В налоговой инспекции составлен реестр налогоплатильщиков, в котором для каждого из них указаны фамилия и сумма уплаченного налога. Упорядочить налогоплатильщиков по убыванию налоговой суммы. В деканате составлена ведомость , в которой указаны фамилия студентов, название предметов и количество прогулов по каждому предмету. Вывести на экран фамилии студентов имеющих максимальное суммарное число прогулов по всем предметам. В деканате составлена ведомость , в которой указаны фамилия студентов, название предметов и количество прогулов по каждому предмету. Вывести на экран фамилии студентов в порядке увеличения их суммарного числа прогулов по всем предметам. Дана таблица стран-участниц олимпийских игр с указанием для каждой из них количества завоеванных золотых серебряных и бронзовых медалей. Упорядочить все страны по убыванию количества золотых медалей. Из двух стран с одинаковым числом золотых медалей выше должна оказаться страна, у которой больше серебряных медалей. Если и здесь равенство, то преимущество должна иметь страна с большим числом бронзовых медалей. 38 8. ОБРАБОТКА ПОСЛЕДОВАТЕЛЬНОСТЕЙ СИМВОЛОВ Пример.1 Вводится последовательность символов, в конце которой стоит точка. Подсчитать общее количество символов, отличных от пробела (не считая точки). #include <stdio.h> void main() { char z; /*z –вводимый символ*/ int k; /*k – количество значащих символов*/ printf (“напишите предложение с точкой в конце\n”); for (k=0; (z=getchar())!=’.’;) if (z!=’ ‘) k++; printf (“\n количество символов= %d”, k); } Пример 2.В заданном стринге удалить все буквы а. #include <stdio.h> main() {int i,j=0; char s[]="acfdakpoakpoka"; for(i=0;s[i]!='\0';i++) if(s[i]!='a') s[j++]=s[i]; s[j]='\0'; printf("%s\n",s); } Пример 3 Ввести стринг и распечатать его, заменив все вхождения буквы а на последовательность символов “abc”. #include <stdio.h> main() #define MAX 100 #define MAXN 200 {int i,j=0; char s[MAX],sn[MAXN]; scanf("%s",s); for(i=0;j<MAXN-1 && s[i]!='\0';i++) 39 if(s[i]=='a'&& j<MAXN-3) {sn[j++]='a'; sn[j++]='b';sn[j++]='c';} else sn[j++]=s[i]; sn[j]='\0'; printf("%s\n",sn); } УПРАЖНЕНИЯ 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. 14. 15. 16. 17. удалить символы, стоящие перед символом *. Рассмотреть случай наличия в последовательности нескольких символов *; подсчитать сколько раз среди символов встречается буква х; исключить все символы между круглыми скобками, включая сами скобки. Рассмотреть случай вложенных скобок; подсчитать наибольшее число подряд идущих пробелов; заменить все восклицательные знаки точками; заменить каждую группу символов NN группой символов Nizhny Novgorod; удалить все символы, не являющимися буквами; распечатать все символы, расположенные между двумя запятыми; подсчитать число вхождений в строку группы символов abc; заменить все прописные латинские буквы одноименными строчными; удалить из каждой группы идущих подряд цифр нули; удалить из каждой группы идущих подряд цифр, все цифры, начиная с третьей; удалить из строки все запятые, предшествующие первой точке; преобразовать строку, удалив из нее каждый символ * и повторив каждый символ, отличный от *; выяснить, входят ли в строку все символы, входящие в слово STRING; проверить, является ли строка палиндромом (выражение, читающееся слева направо и справа налево одинаково); преобразовать строку так, чтобы сначала в ней шли все цифры, а потом все буквы исходной строки; 40 18. выбрать из строки все буквы и отсортировать их в алфавитном порядке; 19. заметь все русские буквы в строке их порядковыми номерами в русском алфавите; 20. подсчитать частоту встречаемости каждой цифры в строке; 21. подсчитать наибольшее число букв А , идущий подряд; 22. реверсировать (расположить в обратном порядке) все символы стоки, расположенные до первой точки; 23. разделить исходную строку на несколько строк длины к. 24. определить содержит ли строка дату в виде хх.хх.хх; 25. ввести строку, содержащую дату в формате хх-месяц-хх и преобразовать ее в формат хх.хх.хх 9. ПРЕОБРАЗОВАНИЕ И ПОСТРОЕНИЕ МАТРИЦ Пример 1. Пусть задана матрица A, размерностью n x n. Необходимо построить матрицу В, причем элементы матрицы строятся по следующей формуле bij max a kl , где область указана ри- l k 1 2 (i,j) k .l сунке. В задачах о выделении областей в матрицах необходимо научиться записывать уравнения изменения индексов при движении по линиям, параллельным главной диагонали, и по линиям, пер- пендикулярным диагонали. Запишем уравнение линий (1) и (2), проходящих через фиксированную точку (i,j). Пусть изменяемые индексы – l и k. Тогда уравнение прямой (1) (см. рис.1) имеет вид: l = j – i + k, а прямая (2) описывается соотношением: l = j + i - k. Области изменения индексов показаны на рисунке. Если необходимо описать заштрихованную область, то это следует делать так, как это делается при описании областей на плоскости. Легко видеть, что индекс k изменяется в пределах от 1 до i. Индекс 41 l удовлетворяет неравенству 1 l n. Область выше линии (1) описывается неравенством l > j – i + k, а область выше линии (2) - l < j + i k. Так как указанная область является пересечением указанных областей, то все перечисленные выше неравенства следует соединять в логическом выражении союзом «и». Таким образом, при построении матрицы В следует воспользоваться четырьмя вложенными циклами, где два внешних описывают индексы матрицы В, то есть изменяются от 1 до n. Что касается двух внутренних циклов, то индекс k изменяется от 1 до i, а индекс l изменяется в пределах от прямой (1) до прямой (2). Ограничения 0 и n следует внести в условие оператора if. Схематически структуру циклов можно изобразить так: i =1 n j =1 n k=1i l= j–i+kj+i–k 1 l n Конец цикла по l Конец цикла по k Конец цикла по j Конец цикла по i Программа решения этой задачи и результаты ее выполнения представлены ниже. #include <stdio.h> #include <conio.h> #define m 6 void main() { int i,j,k,l,n; float a[m][m],b[m][m]; clrscr(); gotoxy(5,5); printf("ПРОГРАММА ПОСТРОЕНИЯ МАТРИЦЫ ПО ЗАДАННОЙ"); gotoxy(5,6); printf(" b(i,j)=max a(k,l), k,l принадлежат"); gotoxy(9,7); printf(" заштрихованной области"); 42 gotoxy(35,10); printf("┌ ┐"); gotoxy(35,11); printf("│ * * * * * * * * * * * * * │"); gotoxy(35,12); printf("│ * * * * * * * * * * * * │"); gotoxy(35,13); printf("│ * * * * * * * * * * * │"); gotoxy(35,14); printf("│ * * * * * * * * * │"); gotoxy(35,15); printf("│ ******* │"); gotoxy(35,16); printf("│ ***** │"); gotoxy(35,17); printf("│ *** │"); gotoxy(35,18); printf("│ * │"); gotoxy(35,19); printf("│ │"); gotoxy(35,20); printf("│ │"); gotoxy(35,21); printf("│ │"); gotoxy(35,22); printf("└ ┘"); getchar();clrscr(); do{ printf("\n\nВведите размерность матрицы <=%d ",m); scanf("%d",&n); }while(!(n>0 && n<=m));clrscr(); for (i=1;i<=n;i++) for (j=1;j<=n;j++){ printf("Введите a(%d,%d)=",i,j);scanf("%f",&a[i-1][j-1]); } clrscr(); printf("ИСХОДНАЯ МАТРИЦА\n"); for (i=1;i<=n;i++){ for (j=1;j<=n;j++) printf("%7.2f",a[i-1][j-1]); printf("\n"); } for (i=1;i<=n;i++) for (j=1;j<=n;j++){ b[i-1][j-1]=-1.e20; for (k=1;k<=n;k++) for (l=j-i+k;l<=j+i-k;l++) if (l>=1 && l<=n && a[k-1][l-1]>b[i-1][j-1]) b[i-1][j-1]=a[k-1][l-1]; 43 } printf("ПОЛУЧЕННАЯ МАТРИЦА\n"); for (i=1;i<=n;i++){ for (j=1;j<=n;j++) printf("%7.2f",b[i-1][j-1]); printf("\n"); } getchar();getchar(); } При выполнении данной программы на экране монитора будет выведено следующее: ПРОГРАММА ПОСТРОЕНИЯ МАТРИЦЫ ПО ЗАДАННОЙ b(i,j)=max a(k,l), k,l принадлежат заштрихованной области ┌ ┐ │* * * * * * * * * * * * * │ │ ************ │ │ *********** │ │ ********* │ │ ******* │ │ ***** │ │ *** │ │ * │ │ │ │ │ │ │ └ ┘ Введите размерность матрицы <=6 4 Введите a(1,1)= 1.00 Введите a(1,2)= 4.00 Введите a(1,3)= 2.00 Введите a(1,4)= -3.60 Введите a(2,1)= 8.90 Введите a(2,2)= -22.10 44 Введите a(2,3)= 5.00 Введите a(2,4)= 0.78 Введите a(3,1)= -3.45 Введите a(3,2)= 2.40 Введите a(3,3)= 9.80 Введите a(3,4)= 6.12 Введите a(4,1)= -23.50 Введите a(4,2)= 1.00 Введите a(4,3)= 7.00 Введите a(4,4)= 89.00 ИСХОДНАЯ МАТРИЦА 1.00 4.00 2.00 -3.60 8.90 -22.10 5.00 0.78 -3.45 2.40 9.80 6.12 -23.50 1.00 7.00 89.00 ПОЛУЧЕННАЯ МАТРИЦА 1.00 4.00 2.00 -3.60 8.90 4.00 5.00 2.00 8.90 8.90 9.80 6.12 8.90 9.80 9.80 89.00 45 l i Пример 2. j i Пусть задана матрица A, размерностью n x n. Необходимо построить матрицу В, причем элементы матрицы строятся по следующей формуле bij min a kl , где область указана k .l рисунке. Область в этом случае следуk ет описать сначала по l, так как этот индекс изменяется в пределах от j до n. Следовательно, внутренние циклы будут: сначала по l от j до n, а затем цикл по k от j+i-l до l-j+i. Так как ищется минимум, то начальное значение следует выбрать достаточно большим. Текст программы и результаты ее работы представлены ниже. #include <stdio.h> #include <conio.h> #define m 6 void main() { int i,j,k,l,n; float a[m][m],b[m][m]; clrscr(); gotoxy(5,5); printf("ПРОГРАММА ПОСТРОЕНИЯ МАТРИЦЫ ПО ЗАДАННОЙ"); gotoxy(5,6); printf(" b(i,j)=min a(k,l), k,l принадлежат"); gotoxy(9,7); printf(" заштрихованной области"); 46 gotoxy(35,10); printf("┌ ┐"); gotoxy(35,11); printf("│ │"); gotoxy(35,12); printf("│ * │"); gotoxy(35,13); printf("│ * * │"); gotoxy(35,14); printf("│ * * * │"); gotoxy(35,15); printf("│ * * * * │"); gotoxy(35,16); printf("│ * * * * * │"); gotoxy(35,17); printf("│ * * * * * * │"); gotoxy(35,18); printf("│ * * * * * │"); gotoxy(35,19); printf("│ * * * * │"); gotoxy(35,20); printf("│ * * * │"); gotoxy(35,21); printf("│ * * │"); gotoxy(35,22); printf("│ * │"); gotoxy(35,23); printf("└ ┘"); getchar();clrscr(); do{ printf("\n\nВведите размерность матрицы <=%d ",m); scanf("%d",&n); }while(!(n>0 && n<=m));clrscr(); for (i=1;i<=n;i++) for (j=1;j<=n;j++){ printf("Введите a(%d,%d)=",i,j);scanf("%f",&a[i-1][j-1]); } clrscr(); printf("ИСХОДНАЯ МАТРИЦА\n"); for (i=1;i<=n;i++){ for (j=1;j<=n;j++) printf("%7.2f",a[i-1][j-1]); printf("\n"); } for (i=1;i<=n;i++) for (j=1;j<=n;j++){ b[i-1][j-1]=1.e20; for (l=j;l<=n;l++) for (k=j+i-l;k<=l-j+i;k++) if (k>=1 && k<=n && a[k-1][l-1]<b[i-1][j-1]) b[i-1][j-1]=a[k-1][l-1]; } 47 printf("ПОЛУЧЕННАЯ МАТРИЦА\n"); for (i=1;i<=n;i++){ for (j=1;j<=n;j++) printf("%7.2f",b[i-1][j-1]); printf("\n"); } getchar();getchar();} При выполнении данной программы на экране монитора будет выведено следующее: ПРОГРАММА ПОСТРОЕНИЯ МАТРИЦЫ ПО ЗАДАННОЙ b(i,j)=min a(k,l), k,l принадлежат заштрихованной области ┌ ┐ │ │ │ *│ │ **│ │ ***│ │ ****│ │ *****│ │ ******│ │ *****│ │ ****│ │ ***│ │ **│ │ *│ └ ┘ Введите размерность матрицы <=6 4 Введите a(1,1)= 2.50 Введите a(1,2)= 3.80 Введите a(1,3)=-2.28 Введите a(1,4)= 4.00 Введите a(2,1)= 6.21 Введите a(2,2)= 9.80 Введите a(2,3)=-3.54 Введите a(2,4)= 6.00 Введите a(3,1)= 1.34 Введите a(3,2)= 6.80 48 Введите a(3,3)=-2.13 Введите a(3,4)= 5.00 Введите a(4,1)= 4.00 Введите a(4,2)= 8.12 Введите a(4,3)= 5.00 Введите a(4,4)= 3.00 ИСХОДНАЯ МАТРИЦА 2.50 3.80 -2.28 4.00 6.21 9.80 -3.54 6.00 1.34 6.80 -2.13 5.00 4.00 8.12 5.00 3.00 ПОЛУЧЕННАЯ МАТРИЦА -3.54 -3.54 -2.28 4.00 -3.54 -3.54 -3.54 6.00 -3.54 -3.54 -2.13 5.00 -3.54 -2.13 3.00 3.00 Пример 3. Дан одномерный массив целых чисел Р размерностью 64. Получить квадратную матрицу порядка 8 ,элементами которой являются числа массива Р, расположенные в ней по схеме, приведенной на рисунке. Эта задача решается с помощью одного основного цикла, в котором организуется управление изменением индексов в зависимости от условий размещения элементов. Для отслеживания направления движения по диагонали вводится вспомогательная переменная l. Ее значение равно 0 при движении вниз по диагонали и 1 при движении вверх. 49 #include<stdio.h> #include<math.h> #include<conio.h> void main() { clrscr(); float p[64]; float a[8][8]; int n=8,i=0,j=0,k,l=0; for (k=0;k<n*n;k++) p[k]=k; for (k=0;k<n*n;k++) { a[i][j]=p[k]; if (j==0 && i<n-1 && l==0 ) { i++ ;l=1; } else if (i==0 && j<n-1 && l==1 ) { j++; l=0;} else if ( j==n-1 && l==1) { i++ ;l=0; } else if (i==n-1 && l==0) { j++; l=1;} else if (l==0) { i++; j--;} else { i--; j++; } } for (i=0;i<n;i++) { for (j=0;j<n;j++) printf("%3.0f ",a[i][j]); printf ("\n"); } } 50 УПРАЖНЕНИЯ Пусть задана матрица A, размерностью n x n. Необходимо построить матрицу В, причем элементы матрицы строятся по следующей формуле bij min a kl , где область указана рисунках 1. k .l 1-10. 2. Пусть задана матрица A, размерностью n x n. Необходимо построить матрицу В, причем элементы матрицы являются средним значением всех элементов матрицы A в заштрихованной области, где область указана рисунках 1-10. 1. 2. (i,j) (i,j) 3. 4. (i,j) (i,j) 51 5. 6. (i,j) (i,j) 7. 8. (i,j) (i,j) 9. 10. (i,j) (i,j) 52 3. Дан одномерный массив целых чисел А размерностью 64. Получить квадратную матрицу порядка 8 ,элементами которой являются числа массива А, расположенные в ней по схемам, приведенным на рис. 11-17 11 12 13 14 53 15 16 17 17 54 ЛИТЕРАТУРА 1. 2. 3. 4. Абрамов С.А., Гнездилова Г.Г., Капустина Е.Н., Семон М.И. Задачи по программированию. - М.:, Наука, 1998. Контрольные задания по информатике для учащихся заочных подготовительных курсов. Сост. В.А.Гришагин, С.Н.Карпенко. Н.Новгород: ННГУ, 2000.-80 с. Сборник задач по программированию. Сост. Е.Е.Манишина, В.Г.Манишин. Н.Новгород: ННГУ, 2000.-78 с. Пильщиков В.Н. Сборник упражнений по языку Паскаль. - М.:, Наука, 1989. 55 Сборник заданий по вычислительному практикуму на языке Си. для студентов механико-математического факультета (специальность математика, прикладная математика, механика) Составители Денисов Вадим Вадимович Маркина Марина Викторовна Сабаева Татьяна Анатольевна Савихин Олег Геннадиевич ___________________________________________ Подписано к печати .Формат 6084 1/16 Печать офсетная. Бумага оберточная. Усл. печ. л. Тираж 300 экз. Заказ .Бесплатно. ____________________________________________________ Нижегородский государственный университет им. Н.И. Лобачевского. 603600 ГСП-20, Н.Новгород, просп. Гагарина, 23. ___________________________________________ Типография ННГУ,603000,Н.Новгород, ул. Б. Покровская 37. ___________________________________________ 56