§ 17. Масівы і структуры як параметры функцый
Сайт: | Профильное обучение |
Курс: | Інфарматыка. 10 клас (Павышаны ўзровень) |
Книга: | § 17. Масівы і структуры як параметры функцый |
Напечатано:: | Гость |
Дата: | Среда, 1 Май 2024, 04:52 |
17.1. Перадача параметра па значэнні і па спасылцы
Па змоўчанні аргументы функцыі ў C++ перадаюцца па значэнні. Калі аргумент перадаецца па значэнні, то яго значэнне капіруецца ў параметр функцыі. Разгледзім прыклад 17.1. У першым выкліку функцыі func аргументам з’яўляецца лік 5. Пры выкліку функцыі ствараецца пераменная k, значэнне 5 капіруецца ў яе. Выконваюцца каманды функцыі, якія працуюць з гэтым значэннем. Затым, калі func завершыць сваю работу, пераменная k знішчаецца. У другім выкліку функцыі аргументам з’яўляецца пераменная x са значэннем 2. Пры выкліку пераменная k ствараецца зноў, і значэнне 2 капіруецца ў k. Пасля завяршэння работы функцыі пераменная k знішчаецца. У трэцім выкліку функцыі аргументам з’яўляецца выраз x + 3, які спачатку вылічваецца (атрымліваем 5), а затым гэта значэнне капіруецца ў пераменную k, якая знішчаецца пасля завяршэння работы функцыі. Паколькі функцыя працуе з копіяй перададзенага значэння, то зыходнае значэнне не можа быць зменена функцыяй (прыклад 17.2). Значэнні пераменных x і y, якія падвоіліся ўнутры функцыі, пасля яе выкліку засталіся не змененымі. Звярніце ўвагу на пераменную k, якая з’яўляецца параметрам функцыі func, а таксама апісана ўнутры main. Для кампілятара гэта зусім розныя пераменныя. У час работы функцыі func значэнне пераменнай k, аб’яўленай у main, невядомае. Іншым спосабам перадачы значэнняў параметраў у функцыі можа быць перадача параметраў па спасылцы. Спасылка — тып пераменнай у C++, які працуе як псеўданім іншага аб’екта ці значэння. Пры аб’яве спасылкі выкарыстоўваецца знак амперсанд (&), які запісваюць паміж тыпам даных і імем спасылкі. Функцыя ў прыклад 17.3 адрозніваецца ад функцыі ў прыкладзе 17.2 тым, што параметр k абвешчаны як спасылка. Пры перадачы параметру па спасылцы копіі перадаваемага аб’ектане ствараецца. Усе дзеянні адбываюцца з тым аб’ектам, на які паказвае спасылка. Розныя спосабы перадачы параметраў маюць свае плюсы і мінусы. Калі параметрамі функцыі з’яўляюцца структуры ці масівы, то іх капіраванне можа прывесці да значнага зніжэння прадукцыйнасці, асабліва калі функцыя выклікаецца шмат разоў. Таксама пры такім капіраванні павялічваецца неабходная колькасць памяці. Таму складаныя тыпы даных перадаюцца звычайна па спасылцы. Пры перадачы параметраў па значэнні адзіны спосаб вярнуць змененае значэнне назад — выкарыстоўваць значэнне функцыі, якое вяртаецца (у камандзе return). Але часам неабходна, каб функцыя змяніла значэнне перададзенага аргумента, а можа быць, не аднаго, а некалькіх. Перадача па спасылцы вырашае ўсе гэтыя праблемы. Пры перадачы значэння па спасылцы магчымы выклік функцыі, параметр якой яшчэ не зададзены (пример 17.4). Значэнне параметра можна вызначыць шляхам уводу з клавіятуры ці з файла або шляхам вылічэнняў. Калі фармальны параметр абвешчаны як спасылка, то фактычным параметрам можа быць толькі пераменная, апісаная да выкліку функцыі. |
Прыклад 17.1. Праграма:
Тэсціраванне. Прыклад 17.2. Праграма:
Тэсціраванне. Прыклад 17.3. Праграма:
Тэсціраванне. Пры выкліку func(x) параметр k становіцца псеўданімам пераменнай x. Такім чынам, усё, што апісана для пераменнай k, будзе адбывацца з пераменнай x. Пасля завяршэння работы функцыі значэнне пераменнай x будзе зменена (павялічыцца ў 2 разы). Наступны выклік func(y) зробіць параметр k псеўданімам пераменнай y, якая таксама зменіць сваё значэнне пасля выканання функцыі. Прыклад 17.4. Праграма:
Тэсціраванне. Значэнні пераменных да выкліку функцыі не вядомыя. Яны будуць вызначаны пры выкліку функцыі і змешчаны па адпаведных адрасах у памяці. Калі ў апісанні такой функцыі зняць спасылку, то пераменныя будуць вызначаны адвольнымі значэннямі. |
17.2. Масівы як параметры функцый
Прыклад 17.5. Дадзены натуральныя n, m цэлыя a0,..., an – 1, b0,..., am – 1, атрымаць:
Этапы выканання задання I.Зыходныя даныя: пераменныя n і m — колькасць элементаў у масівах а і b, a і b — лінейныя масівы. II. Вынік: значэнне пераменнай t. III. Алгарытм рашэння задачы. 1. Увод зыходных даных. Для ўводу масіву створым функцыю. Паколькі да выкліку функцыі памер вектара невядомы, то вектары a і b ствараюцца без вызначэння колькасці элементаў у іх. Для ўводу значэнняў можна выкарыстоўваць адзін з двух варыянтаў: 1.1. Увесці колькасць элементаў, змяніць памер вектара з дапамогай функцыі resize (гл. Дадатак да главы 1), затым увесці элементы. 2. Для знаходжання мінімальнага і максімальнага элементаў масіву аформім адпаведныя функцыі. Функцыя будзе прымаць масіў як параметр і вяртаць значэнне мінімальнага (максімальнага) элемента ў масіве. |
Прыклад 17.5. V. Праграма:
VI. Тэсціраванне. |
17.3. Пошук зададзенага элемента ў шматмерным масіве
Пры арганізацыі лінейнага пошуку ў аднамерным масіве для праверкі складаных умоў пошуку стваралі функцыі, якія правяралі асобны элемент. Пры рабоце з двухмернымі масівамі можна паступіць аналагічна. У гэтым выпадку функцыя будзе прымаць у якасці параметра лінейны масіў і апрацоўваць яго. Прыклад 17.6. Зададзены двухмерны масіў a з m радкоў і n слупкоў. Атрымаць лінейны масіў b, у якім b[i] — сума элементаў i-га радка масіву a, кратных 3. Этапы выканання задання I. Зыходныя даныя: пераменныя n і m — колькасць радкоў і слупкоў у масіве а, a — двухмерны масіў. II. Вынік: лінейны масіў b. III. Алгарытм рашэння задачы.
IV. Апісанне пераменных: n, m – int, a – vector<vector<int>>, b – vector<int>. Прыклад 17.7. Зададзены двухмерны масіў a з m радкоў і n слупкоў. Вывесці нумары радкоў, элементы якіх утвараюць узрастаючую паслядоўнасць. Калі такіх радкоў у масіве няма, то ўвесці адпаведнае паведамленне. Этапы выканання задання I.Зыходныя даныя: пераменныя n і m — колькасць радкоў і слупкоў у масіве а, a — двухмерны масіў. II. Вынік: нумары радкоў і паведамленне, што радкоў няма. III. Алгарытм рашэння задачы.
2.1. Элементы ўтвараюць узрастаючую паслядоўнасць, калі кожны наступны большы за папярэдні.
|
Прыклад 17.6. V. Праграма:
VI. Тэсціраванне. Прыклад 17.7. V. Праграма:
VI. Тэсціраванне. |
17.4. Масівы структур. Пошук у масіве структур
Прыклад 17.8. У тэкставым файле input.txt захоўваецца інфармацыя пра студэнтаў. Для кожнага студэнта паказана яго прозвішча, горад, з якога ён прыехаў (назва горада — адно слова), і тры лікі — балы за ЦТ, з якімі ён паступіў у ВНУ. Палічыць колькасць студэнтаў, у якіх сума балаў большая за x (уводзіцца з клавіятуры). Вывесці ў тэкставы файл з імем otchet.txt прозвішчы і сумарны бал студэнтаў з паказанага горада (уводзіцца з клавіятуры). Этапы выканання задання I. Зыходныя даныя: структура student з палямі fam, gorod, otm (масіў з трох элементаў). Даныя счытваюцца ў масіў структур. II. Вынік: спіс студэнтаў з паказанага горада ў файле і колькасць студэнтаў з сумарным балам, большым за x, на экране. Калі пошук не даў выніку, то вывад адпаведнага паведамлення. III. Алгарытм рашэння задачы.
2.1. Функцыя для пошуку па балах find_ball вяртае ў якасці выніку лік студэнтаў. Калі функцыя вярнула значэнне 0, то такіх студэнтаў няма.
IV. Апісанне пераменных: n – int, a – vector<student>. Перадача параметраў па спасылцы дазваляе пераслаць вялікія структуры ці масівы з мінімальнай затратай рэсурсаў. Аднак тут таксама могуць узнікнуць іншыя праблемы. Спасылкі дазваляюць функцыі змяняць значэнні аргументаў напрамую. Аднак гэта можа быць непажадана, калі трэба, каб аргумент быў даступны толькі для чытання. У такім выпадку можна выкарыстоўваць перадачу параметра па канстантнай спасылцы. Канстантная спасылка — спасылка на пераменную, значэнне якой немагчыма змяніць праз гэту ж спасылку. Для таго каб спасылка была канстантнай, трэба дабавіць перад апісаннем ключавое слова const. Калі выкарыстоўваць канстантную спасылку ў якасці параметра функцыі, то функцыя не зменіць аргумент. Пры спробе гэта зрабіць атрымаем памылку кампіляцыі (прыклад 17.9). |
Прыклад 17.8. V. Праграма:
VI. Тэсціраванне Прыклад 17.9. Праграма: |
Пытанні к параграфу
1. Што адбываецца ў функцыі пры перадачы параметраў па значэнні? 2. Як перадаць параметр функцыі па спасылцы? 3. Для якіх даных рэкамендуецца перадача параметра по спасылцы? 4. Навошта можа быць выкарыстана перадача параметра па канстантнай спасылцы? |
Практыкаванні
1. Для задачы з прыкладу 17.5 выканайце пералічаныя заданні.
1. Пералічыце сітуацыі, якія належаць да «астатніх выпадкаў» ва ўмове задачы.
2. Змяніце праграму так, каб для «астатніх выпадкаў» выводзіліся значэнні і
2. Дадзены натуральныя n, m, k цэлыя a0, ..., an-1, b0, ..., bm-1, c0, ..., ck-1, атрымаць:
1.
2.
3.
3. Дадзены натуральны n і цэлыя x0, ..., xn – 1, y0, ..., yn – 1. Атрымаць:
1.
2.
Запіс абазначае суму ўсіх xi пры змяненні i от 0 да n – 1: x0 + x1 + ... + xn – 1.
4. Зададзены двухмерны масіў a з m радкоў і n слупкоў. Атрымаць лінейны масіў b, у якім b[i] — это:
- Колькасць дадатных элементаў i-га радка масіву a.
- Цэлая частка сярэдняга арыфметычнага i-га радка масіву a.
- Мінімальны элемент i-га радка масіву a.
- Колькасць лікаў, модуль якіх роўны модулю максімальнага элемента i-га радка масіву a.
- Колькасць лікаў, якія пры дзяленні на 3 і на 5 даюць аднолькавыя астачы.
- Лік, які сустракаецца ў i-м радку масіву a часцей іншых лікаў. Калі такіх лікаў некалькі, то ўзяць лік з меншым нумарам у радку.
- Рэалізаваць пункты 1—6 для слупкоў. Для гэтага транспаніраваць матрыцу (гл. прыклад 15.13).
5. Зададзены двухмерны масіў a з m радкоў і n слупкоў.
- Вывесці нумары радкоў, якія змяшчаюць мінімальны элемент двухмернага масіву.
- Вывесці нумары радкоў, у якіх ёсць роўныя элементы. Калі такіх радкоў няма, то вывесці адпаведнае паведамленне.
- Вывесці нумары радкоў, у якіх усе элементы розныя. Калі такіх радкоў няма, то вывесці адпаведнае паведамленне.
- Вывесці нумары радкоў, сумы элементаў у якіх роўныя. Вывад ажыццявіць у выглядзе табліцы.
Прыклад |
Тлумачэнне |
0: 1: 2, 3 2: 3 3: 4: 5 5: |
Сума элементаў першага радка роўна суме элементаў 2-га і 3-га радкоў, сума элементаў 2-га радка роўна суме элементаў 3-га радка. Сума элементаў 4-га радка роўна суме элементаў 5-га радка. Для радкоў 0 і 3 няма радкоў з роўнымі ім сумамі. Для кожнага радка правяряюцца толькі радкі з нумарамі, якія большыя, чым нумар бягучага радка. |
5. Рэалізаваць пункты 1—4 для слупкоў. Для гэтага транспаніраваць матрыцу (гл. прыклад 15.13).
6. Унясіце змяненні ў праграму прыкладу 17.8 так, каб праграма карэктна апрацоўвала назвы гарадоў, якія складаюцца больш чым з аднаго слова (напрыклад, Старыя Дарогі ці Ніжні Ноўгарад).
7. Стварыць тэкставы файл апісанай ніжэй структуры. У першым радку ў тэкставым файле запісаць колькасць даных. Колькасць даных павялічыць да 10, падабраўшы патрэбную інфармацыю. Вывесці ў тэкставы файл з імем otchet.txt даныя, якія задавальняюць пералічаныя ўмовы.
1. У файле захоўваюцца: назва краінны[1], сталіца, плошча (тыс. км2) і колькасць насельніцтва (млн чал.):
Беларусь Мінск 208 9.41
Расія Масква 17075 143.3
ЗША Вашынгтон 9373 310.2
Канада Атава 9985 34.2
Францыя Парыж 547 65.4
І г.д.
Знайсці колькасць краін з насельніцтвам <=50 млн чал. і тыя краіны, назва сталіцы якіх складаецца з k (уводзіцца з клавіятуры) літар.
2. У файле захоўваюцца: назва вытворцаў пральнай машыны, яе мадэль, магутнасць і максімальная загрузка бялізны (кг).
Samsung WW65K52E69S 2400 6.5
Bosch WLT24440OE 2300 7
Haier HW70-BP12758S 1900 7
LG F12M7NDS0 1700 6
И т.д.
Знайсці колькасць пральных машын з магутнасцю >2000 і назвы вытворцаў, у мадэль якіх уваходзіць літара «х» (значэнне «х» уводзіцца з клавіятуры)
3. У файле захоўваюцца: назва возера[2], вобласць, у якой яно размешчана; яго аб’ём (млн м3), плошча (км2), максімальная глыбіня (м) і празрыстасць (м).
Нарач Мінская 710 79.6 24.8 7.4
Снуды Вшцебская 107 22 16.5 6.6
Рычы Віцебская 131.5 12.9 51.9 5.5
Свіцязь Гродненская 7.76 25.2 15 5.2
І г.д.
Знайсці самае глыбокае і самае празрыстае возера (вывесці назву і месцазнаходжанне), а таксама назвы тых азёр, якія знаходзяцца ў паказанай вобласці (увесці з клавіятуры).
[1] http://ostranah.ru/ – геаграфічны даведнік «Аб краінах» (дата доступу: 20.06.2020).
[2] http://rad.org.by/articles/voda/10-samyh-... і https://ru.wikipedia.org/wiki/Озёра_Белоруссии (дата доступу 20.06.2020).