- съставно условие
- алгоритъм на Евклид
- естествено число - прости делители
- решето на Ератостен
- цифри и числа
- побитови операции
- точност при извеждане
- проверка на входни данни
- наредба - сортиране
- сортиране - пряк избор
- сортиране - вмъкване
- сортиране размяна
- сливане на редици
- вмъкване на елемент
- двумерен масив
- диагонал в матрица
- матрица
- матрица - транспониране
- матрица - събиране
- матрица - умножение
- множество - елементи
- множество - допълнение
- множества - обединение
- множества - разлика
- множества - сечение
- линейно уравнение
- квадратно уравнение
- полином
- рекурсия - итерация
- числов триъгълник
- минимална стойност
- средна стойност
- факториел
- числа на Фибоначи
- Питагорова тройка числа
- палиндром - решена задача
- алчен алгоритъм
- египетски дроби
- комбинации
Точност при извеждане на реални числа
закръгляване на реални числа
закръгляне при делене на цели числа
верижни дроби
точност при изчисление - сума от дроби
египетски дроби
Ще наричаме ирационално число такова число, което не може да бъде преставено като обикновена дроб с числител и знаменател цели числа. Друго подобно определение за ирационално число е безкрайна непериодична десетична дроб.
Примери за ирационално число са често използвани константи като:
√2 = 1.414 213 562 373 095 048 801 688 724 209 698 078 ...
√3 = 1.732 050 807 568 877 293 527 446 341 505 872 366 ...
π = 3.141 592 653 589 793 238 462 643 383 279 ...
e = 2.718 281 828 459 045 235 360 287 471 352 ...
φ = 1.618 033 988 749 894 848 204 586 834 365 ...
Същите числа, но в двоична бройна система, могат да бъда представени така:
√2 = 1.011 010 100 000 100 111 100 110 011 001 111 ...
√3 = 1.101 110 110 110 011 110 101 110 100 001 011 ...
π = 11.001 001 000 011 111 101 101 010 100 010 001 ...
e = 10.101 101 111 110 000 101 010 001 011 000 101 ...
φ = 1.100 111 100 011 011 101 111 001 101 110 010 ...
Под точност на извеждане на числа ще разбираме с колко цифри можем да представим дадена стойност, дадено отношение между стойности, как се извършва закръгляване на стойност или по-общо как се осъществява представяне на реални числа в паметта на компютъра. Нека имаме две цели числа, за които трябва да изчислим стойност на тяхното отношение. Всяка въведена / изчислена стойност се съхранява в паметта на компютъра до определена точност. Декларираният тип на променливата определя допустимият числов интервал и възможния брой двоични разряди за съхраняване на въведената или изчислена стойност на тази променлива. Използвания брой разряди за въведено или пресметнато число предопределят до известна степен неговата точност при извеждане, но не е винаги пресметната стойност е идентична с изведената. Въведените числа винаги се закръглят след определен брой знаци. Това се отнася както за рационални числа и/или периодични дроби, така и за ирационални числа. Целта ни тук е извеждане на стойност представена като отношение на две естествени числа. Самото извеждане се извършва с точност до определен брой цифри след десетичната запетая и не е свързано със вече съхранената стойност за същото отношение числител / знаменател.
закръгляване на реални числа
Да се състави програма, която по въведени 2 естествени числа от интервала [100..10000] се осъществява закръгляване при извеждане резултата от деленето им с точност 25 знака след десетичната запетая. При цялата част на това отношение се ползва тривиално извеждане. За дробната част ще се ползва цикъл, чрез който след всяко делене умножаваме числителя по 10. Да припомним: ако делители на знаменателя са само степени на 2 и 5 е възможно получаване на стойност, която е крайна, непериодична дроб. Пример: 4,3 Изход: 1.3333333333333333333333333
Следващата примерна програма дава решена задача за точност при извеждане на отношение между две естествени числа:
#include<iostream> using namespace std; const int razr=25;//broj cifri sled desetichnata zapetaq void deliteli(int a, int b) //funkciq za izwevdane na rezultat ot delene { int ob; double a1; a1=a; a1/=b;//normalno delene cout<<"Ako se izwyrshwa delene "<<a<<"/"<<b<<" to rezultata e: "<<a1<<endl; cout<<"Rezultatyt move da byde predstawen e kato: "; cout<<a/b<<".";//izwevda samo cqlata chast a=(a%b)*10;//na wsqka stypka ot ciklyla chislitelq se umnnovawa po 10 for (ob=0;ob<razr;ob++)//do ukazaniq broj sled desetichnata tochka { cout<<a/b;//izwevda poredmata posledna cifra w drobnata chast na chisloto a=(a%b)*10; }//realizirame delene chrez posledowatelno umnovenie po 10 na ostatyka cout<<endl; } //void deliteli int main() //nachalo na programata { int c,d; cout<<"Da se systawi programa, koqto po wywedeni 2 estestweni chisla \n"; cout<<"ot interwala [100..10000] izwevda rezultat ot deleneto im s \n"; cout<<"tochnost 25 znaka sled desetichnata zapetaq.\n"; cout<<"Whodni danni 2 estestweni chisla. \n"; cout<<"Primer: 4,3 Izhod 1.333333333333333\n"; cout<<"Wywedete chislitel chislo ot interwala [10..10000]: ";cin>>c; cout<<"Wywedete znamenatel chislo ot interwala [10..10000]: ";cin>>d; deliteli(c,d); system("pause"); return 0; }//kraj na programa chisla - tochnost
закръгляне при делене на цели числа
В някои от алгоритмите се налага закръгляне на цели числа, т.к. се търси най-близкото цяло число като частно и/или като остатък при делене на две естествени числа. При представяне на число от една бройна система в друга имаме отношение между въведеното число и числото основа на новата бройна система. При изчисляване на това отношение се налага закръгляне на цели числа, т.к. постоянно се работи с целочислено частно и целочислен остатък. Примери за алгоритми използващи закръгляне на цели числа при извеждане стойност на отношение между две естествени числа има достатъчно много. Нека разгледаме следната примерна задача за закръгляне на цели числа:
Имаме две естествени числа M и N, където M>N. Тези числа са съответно числител и знаменател в дадено отношение. Трябва да се изведат две нови числа P и Q, които са кратни на N и съответно са най-близкото по-малко и най-близкото по-голямо на N.
Алгоритъм
Тази задача се свежда до закръгляне на стойност, т.к. се търси целочислено частно
въвеждаме стойност на двете естествени числа, като проверяваме за релацията M>N;
изчисляваме стойност на целочислено частно чрез целочислено делене на двете естествени числа;
използваме целочисления остатък O за закръгляне на търсените цели числа;
по-малкото естествено число има стойност P = M – O;
по-голямото естествено число има стойност Q = M +(N – O);
Подобни въпроси са разгледани и в египетски дроби, закръгляване на реално в цяло число, точност при извеждане на стойност, манипулатори oct, dec, hex.
Следващата примерна програма илюстрира алгоритъм за закръгляне с цели числа
#include <iostream> using namespace std; int main() { int m,n,o,p,q; cout<<"Imate dwe estestweni chisla m>n ot interwala [2..102].\n"; cout<<"Dwete chisla sa chislitel i znamenatel, tyrsim stojnost \n"; cout<<"na tqhnoto zakrygleno chastno.\n"; cout<<"She tyrsim dwe drugi estestweni chsila p i q, koito sa\n"; cout<<"naj-blizki do m i udowletworqwat iziskwaneto p<m<q.\n"; cout<<"Primer m=14 n=5 Izhod: p=10, q=15\n"; do { cout<<"Wywedete chislitel m: "; cin>>m; cout<<"Wywedete znamenatel n: "; cin>>n; } while (m<n); o = m % n; //stojnost na celochislen ostatyk p = m - o; q = m + (n-o); cout<<"naj-blizkoto zakrygleno po-malko chislo "<<p<<endl; cout<<"naj-blizkoto zakrygleno po-golqmo chislo "<<q<<endl; system("pause"); return 0; }//kraj na programa zakryglqwane na celi chisla
верижна дроб
В математиката терминът верижна дроб се свързва с редица от отношения между естествени числа, в която всеки следващ член формира нов знаменател в същата дроб. Възможно е първият член в тази редица да е естествено число. Приемаме следните означения: a, b са естествени числа и представляват съответно числител и знаменател. Разглежданите в математиката видове дроби най-често са:
проста дроб a < b Пример: 3 / 8
смесена дроб a > b Пример: 6 / 4, 9 / 5
непериодична дроб – знаменателят е съставен само от делители 2 и 5. Пример: 102 / 10 = 10.2
периодична дроб - знаменателят или просто число или неговите делители не са само 2 и 5. Пример:4 / 3 = 1.3(3)
верижна дроб - знаменателят на тази дроб е описан с ред, в който всеки член формира нов знаменател в същата верижна дроб.
Изчислението на дадена верижна дроб е свързано със следните проблеми:
а) точността е ограничена от използваните типове променливи;
При използване на включената в езика библиотека #include <iomanip.h> е възможно да посочим желана точност на извеждане с setprecision(естествено число). Но това е валидно до определени граници т.к. числата са представен в компютърната памет в експоненциален вид. Пример: за деклариране на достатъчно малко число за точност.
const double EPSILON = 1E-14;
б) по сериозен проблем представлява оформянето на самата формула за изчисляване на верижна дроб.
Подобен тип задачи се решават в “обратна” посока, т.е. първо се изчислява стойността на последния член и тя се предава за изчисляване на предпоследния член. Този ред на изчисления продължава до достигане на най-левия член.
Очевидно, в случая е удобно да се приложи рекурсивна функция.
Алгоритъмът е приложим при сходящи редици, т.е. всеки десен член има много-по-малка тежест за крайния резултат – стойността на изчисляваната верижна дроб.
Ирационалните числа са безкрайни, непериодични дроби и не могат да се представят като отношение a / b;
Крайните десетични дроби могат да се разглеждат като безкрайни периодични дроби с период 0.
Да разгледаме следната примерна задача за верижна дроб за изчисляване приближена стойност на ирационалното число на Лудолф:
Дадена е верижна дроб, описана със следното уравнение:
3+ 1/(6+ 9/(6+25/(6+49/(6+81/(6+121/....)))
Да се състави програма, чрез която по въведен N - брой членове на верижната дроб се извърши изчисляване на стойността й.
Пример: 12 Изход: 3.14148.
Следващата примерна програма реализира изчисляване на верижна дроб:
#include <iostream> #include <cmath> using namespace std; double tyrsi_pi(double i,int j) {double s; if(j<1) return 0;//broq chlenowe i dyno na rekursiq s=sqrt(i);//wzema koren kwadraten ot predhodniq chislitel s+=2;//za da formira (i+2)^2 s*=s;//kwadrata na sledwashoto chislo cout<<"Porednata werivna drob e: "<<i<<"/"<<s-i<<"+"<<s<<endl; j--;//dynoto na rekursiqta e stojnost 0 return i/( 6+tyrsi_pi(s,j) ); }//rekursiq werivna drob int main() { double nach=1; int broi; double rezult; char ose='y'; cout<<"Dadena e werivna drob, opisana sys slednoto urawnenie:\n"; cout<<"3+1/(6+ 9/(6+25/(6+49/(6+81/(6+121/.. .)))\n"; cout<<"Da se systawi programa, koqto chrez rekursiwna funkciq izchslqwa \n"; cout<<"stojnostta na werivnata drob za opredelen broj chlenowe.\n"; cout<<"Primer:12 Izhod 3.14148.\n"; while (ose=='y') {cout<<"Kolko chlena ot werivnata drob da izpolzwam: ";cin>>broi; rezult=3+tyrsi_pi(nach, broi); cout<<" Izpolzwanata rekursiwna funkciq wrysha slednata stojnost: "<<rezult<<endl; cout<<"Za srawnenie, tyrsenata stojnost e: "<<3.1415925<<endl; cout<<"Velaete li druga prowerka <y/n>: ";cin>>ose; } system("pause"); return 0; }//kraj na programa werivna drob точност при изчисление - сума от дроби
Да разгледаме следата задача - търси се сумата: x^0 + x^1/1! +x^2/2! + x^3/3! +....x^n/n!, където x,n са естествени числа.
Алгоритъм:
Стойностите се съхраняват в оперативната памет като реални числа с ограничена точност. За формиране на сумата от дроби е необходимо изчисляване на числител и знаменател на всяка отделна дроб. Така могат да се оформят два отделни алгоритъма:
а) всяка от участващите дроби се изчислява отделно - увеличава се сложността на алгоритъма, както и точността при изчисление на крайната сума от дроби. Грешката от закръгление се явява като сума от грешките при изчисляване на всяка отделна дроб.
б) всяка от следващите дроби се получава като произведение с множители: стойност на предходната дроб и множител x/n. Тук точността при изчисление зависи и от грешката на закръгление получена от предходната дроб, но се намалява сложността на алгоритъма.
Примерната блок схема отразява втория алгоритъм.
Следващата примерна програма реализира изчисляване на сума от дроби:
#include <iostream> using namespace std; int main() { double S,m,k,d,x; int i,n; cout<<"Wywedete X [1..10]: ";cin>>x; cout<<"Wywedete broi n [5..20]: ";cin>>n; S=d=m=1; for (i=1;i<=n;i++) {d*=x/i; S+=d; cout<<"poredna drob: "<<d<<" natrupana suma: "<<S<<endl; } cout<<"suma S="<<S<<endl; system("pause"); return 0; }//kraj programa drobi Обяснени и решени задачи с подобни алгоритми, функции и служебни думи са разгледани в страницата с електронни уроци по информатика - програмиране.
Илюстриране работата на характерни алгоритми можете да намерите в предоставените електронни помагала съдържащи решени задачи, примери.