Студопедия Главная Случайная страница Обратная связь

Разделы: Автомобили Астрономия Биология География Дом и сад Другие языки Другое Информатика История Культура Литература Логика Математика Медицина Металлургия Механика Образование Охрана труда Педагогика Политика Право Психология Религия Риторика Социология Спорт Строительство Технология Туризм Физика Философия Финансы Химия Черчение Экология Экономика Электроника

Вторичная полость тела (целом): происхождение, строение, основные функции




 

У мові програмування C існує велика кількість різноманітних цілочисельних типів даних, області визначення яких охоплюють числа різних діапазонів. При вирішенні завдання програміст повинен вибрати правильні типи даних для числових змінних, виходячи з природи відповідних даних, а також вимог до займаної програмою і її даними пам'ятті і бажаною швидкодією. Тим не менш, діапазони вбудованих цілочисельних типів даних мови C обмежені, що не дозволяє виконувати обчислення над досить великими числами (наприклад, з розрядністю більше 20 десяткових цифр). Таке обмеження виявляється серйозною перешкодою при вирішенні завдань, природа яких вимагає виконання операцій над великими числами, наприклад завдань, що вимагають обчислення елементів швидкозростаючих послідовностей. Зокрема, використання типу int мови C для обчислення елементів послідовності Фібоначчі дозволяє отримати лише 46 перших чисел, після чого відбувається цілочисельне переповнення, і отримання наступних елементів стає неможливим.

Така проблема обмеженості діапазонів цілочисельних типів даних вирішується за допомогою так званої "довгої арифметики". Довга арифметика - в обчислювальній техніці операції над числами, розрядність яких перевищує довжину машинного слова даної обчислювальної машини.

На практиці довга арифметика застосовується в наступних випадках:

• на комп'ютерах з процесорами низької розрядності і мікроконтролерах. Наприклад, на комп'ютерах і мікроконтролерах з 8- бітними процесорами без використання довгої арифметики неможливо виконати ніякі нелбхідні обчислення;

• при вирішенні завдань криптографії;

• при створенні математичного та фінансового програмного забезпечення, вимоги до точності обчислень в якому дуже високі і критичні, а помилки округлення та переповнення неприпустимі;

• для обчислень знаменитих трансцендентних чисел ( , e і т. д.) з високою точністю;

• для вирішення олімпіадних завдань з програмування.

Розглянемо, яким чином можна зберігати довгі цілі числа в пам'яті комп'ютера і як виконувати над ними дії. Зазвичай довге число представляють у вигляді масиву, елементи якого зберігають цифри довгого числа, і окремо додатково збережемо довжину числа, тобто кількість значущих цифр. При зберіганні довгого числа зручніше перейти від десяткової системи числення до системи числення з більшою основою, так як це дозволить краще використовувати простір оперативної пам'яті, використовуваної під масив. Кількість значущих цифр будемо зберігати в першому елементі масиву ( елементі з індексом 0). Цифри числа будемо зберігати в зворотному порядку, тобто молодша цифра буде зберігатися в елементі масиву з меншим індексом.

Зробимо наступні оголошення:

#include <stdio.h>

#include <conio.h>

/// максимальна довжина числа - 1000 знаков

#define NUMMAX 1000

/// основа системи числення довгих чисел - 10^9

#define NUMBASE 1000000000

/// отримати довжину числа

#define NUMLEN(n) ((n)[0])

/// визначення типу довгих чисел

typedef int number_t[NUMMAX + 1];

 

Таким чином, ми визначили тип даних довгих чисел - number_t. З його допомогою можна зберігати й обробляти числа довжиною до 9000 десяткових знаків. Основа системи числення вибрана рівною 109, це дозволяє зберігати в одному елементі масиву до 9 десяткових знаків. Розглянемо приклад зберігання двох чисел: 1 і 1234567890 .

Число 1 менше обраної основи системи числення, тому воно буде представлено однією значущою цифрою і для його зберігання буде достатньо 1 елемента масиву. Схема вищенаведеного опису може бути наступною:

Число 1234567890 більше обраної основи системи числення, тому воно буде представлено двома значущими цифрами і для його зберігання потрібно 2 елемента масиву. Схема наведеного опису може бути наступною:

Створимо три допоміжні функції, які виконують установку значення довгого числа. Функція numzero ( ) встановлює довге число рівним нулю. Програмний код функції:

 

/// Скидання довгого числа в нуль

void numzero (number_t lhs)

{

lhs[0] = 1;

lhs[1] = 0;

}

Функція numassgns ( ) присвоює довгому числа коротке значення з діапазону 0 .. 232-1:

 

/// Присвоювання короткого числа довгому числу

void numassgns (number_t lhs, unsigned rhs)

{

lhs[0] = 0;

while (rhs)

{

lhs[++lhs[0]] = rhs % NUMBASE;

rhs /= NUMBASE;

}

}

Функція numassgn ( ) присвоює одному довгому числу значення іншого довгого числа:

 

/// Присвоювання довгих чисел

void numassgn ( number_t lhs , const number_t rhs )

{

int i ;

// Переписуємо довжину результуючого числа

lhs [0] = rhs [0];

// Копіюємо цифри

for ( i = 1; i <= NUMLEN ( rhs ) ; ++ i )

lhs [ i ] = rhs [i] ;

}

Для виведення довгого числа на екран створимо функцію numprint ( ). Дана функція спочатку перевіряє довжину числа, і якщо вона дорівнює 0, то виводить число 0, в іншому випадку вона друкує цифри числа на екрані проходячи по масиву у зворотному напрямку, від індексів з великими значеннями до індексів з меншими значеннями, так як цифри числа зберігаються у зворотному порядку:

 

/// друк довгого числа

void numprint (const number_t lhs)

{

int i;

printf ("%d", NUMLEN (lhs) ? lhs[NUMLEN (lhs)] : 0);

for (i = NUMLEN(lhs) - 1; i > 0; --i)

printf ("%09d", lhs[i]);

}

Операція складання довгих чисел реалізує звичайне складання чисел стовпчиком. Якщо необхідно скласти два числа 12345 і 678. Записуємо ці два числа в стовпчик таким чином, щоб молодші розряди числа виявилися один під одним. Після цього по таблиці додавання складаємо незалежно розряди один з одним. Якщо результат перевершує 9, то запам'ятовуємо 1, переносимо її в старший розряд, а в поточному розряді записуємо молодший розряд від результату складання. І так продовжується до тих пір, поки всі розряди не будуть враховані. Зверніть увагу, що якщо довжина чисел різна, то в старших розрядах більш довгого числа додавання проводиться тільки з " запомненою" 1 переносу. Схема обчислень може бути наступною:

 

Додавання чисел виконується функцією numadd(). Функція приймає два числа - доданків і записує результат в параметр з ім'ям res. Функція вибирає з двох доданків більш коротке і спочатку складає розряди двох чисел, потім, коли всі розряди більш короткого числа будуть враховані, додає розряди, що залишилися, більш довгого числа з урахуванням перенесення, ознака якого зберігається у змінній c. Так як цифри числа зберігаються в зворотному порядку, то складання здійснюється в порядку зростання індексів масиву.

 

/// Додавання довгих чисел

void numadd (number_t res, const number_t lhs, const number_t rhs)

{

int i = 0;

// флаг переноса

int c = 0;

// число з мінімальною довжиною

const int *sn = NUMLEN (lhs) < NUMLEN (rhs) ? lhs : rhs;

// число с максимальною довжиною

const int *ln = sn == lhs ? rhs : lhs;

 

// додаємо два числа

while (i < NUMLEN (sn))

{

++i;

res[i] = c + sn[i] + ln[i];

c = res[i] > NUMBASE ? 1 : 0;

if (c) res[i] -= NUMBASE;

}

// додаємо залишок від більш довшого числа і перенос

while (i < NUMLEN (ln))

{

++i;

res[i] = c + ln[i];

c = res[i] > NUMBASE ? 1 : 0;

if (c) res[i] -= NUMBASE;

}

// враховуємо останній перенос

if (c) res[++i] = c;

// зберігаємо довжину числа

res[0] = i;

}

Приклад використання арифметики довгих чисел. Функція main ( ) створює три змінні для зберігання довгих чисел, ініціалізує значеннями, і виконує операцію складання, після чого друкує результат на екрані. Програмний код головної функції:

 

int main()

{

number_t a, b, c;

numassgns (a, 1234567890);

numassgns (b, 1);

numadd (c, a, b);

numprint (c);

printf("\n\n ... Press any key: ");

_getch();

return 0;

}

Завдання:

1. Створіть функцію numtoa ( ) , що виконує перетворення довгого числа в рядок. Функція повинна мати наступний прототип :

/ / / Переклад довгого числа в рядок

void numtoa ( const number_t num , char * str ) ;

2. Створіть функцію atonum ( ) , що виконує перетворення рядка в довге число. Функція повинна мати наступний прототип :

/ / / Переклад рядка в довге число

void atonum ( const char * str , number_t num ) ;

3. Розробіть програму, що виконує обчислення 500 перших чисел послідовності Фібоначчі Елементи послідовності Фібоначчі обчислюються за наступним рекурентним співвідношенням:

Вторичная полость тела (целом): происхождение, строение, основные функции.

Происхождение (и строение)

1) Энтероцельное. Целомические мешки образуются из выростов кишечника.

 


А – впячивание у гаструлы

В – отделение кишечных выростов

С – вытеснение целомом первичной полости

1 – эпидермис

2 – базальная пластинка

3 – первичная полость

4 – гастродермис

5 – полость кишечника

6 – мезодермис (=целотелий)

7 – целом


 

2) Телобластический. Целомические мешки возникают как полости в полосках мезенхимы (которые образуются из телобластов)







Дата добавления: 2015-06-15; просмотров: 444. Нарушение авторских прав


Рекомендуемые страницы:


Studopedia.info - Студопедия - 2014-2020 год . (0.013 сек.) русская версия | украинская версия