Студопедия

КАТЕГОРИИ:

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

ФУНКЦІЇ ПЕРЕВІРКИ ДІАПАЗОНУ




На практиці досить широко використовуються функції перевірки приналежності символів якому-небудь діапазону, такі як isalnum, isalpha, isascii, isdigit і т.д., оголошені в заголовному файлі ctype.h. Синтаксис цих функцій має вигляд:

int isrange ( int c ) ;

Якщо параметр належить діапазону, то функція повертає число, більше нуля, а якщо ні, то – нуль. Нижче розглядається приклад використання цього виду функцій.

#include <ctype.h>

#include <iostream.h>

void main ()

{

char Age [4] ; // оголошення рядка із трьох символів, у якій зберігається вік

char S [81] ;  // оголошення рядка повідомлень із вісімдесяти символів

unsigned int i ; // оголошення цілої змінної без знака - номер символу

for ( ; ; )          // нескінченний цикл

{

begin:   // оголошення мітки – початок циклу

Chartooem ( "Ведіть свій вік, будь ласка ", S ) ;

cout << S ;                                 // друк запрошення

cin.getline ( Age, 4 ) ;               // уведення віку

for ( i=0 ; i<strlen ( Age ) ; i++) // для всіх символів рядка Age

{

if ( isalpha ( Age [ i ] ) )    // якщо i–й символ є буквою

{

Chartooem ( "\n\t\t Ви ввели букву, спробуйте знову \n\n", S ) ;

сout << S ; goto begin ; // друк повідомлення й перехід у початок циклу

}

if ( iscntrl ( Age [ i ] ) )      // якщо i–й символ є керуючим

{

Chartooem ( "\n\t\t Ви ввели керуючий символ, спробуйте знову \n\n", S) ;

cout<<S ; goto begin ; // друк повідомлення й перехід у початок циклу

}

if ( ispunct ( Age [ i ] ) )    // якщо i–й символ є символом пунктуації

{

Chartooem ( "\n\t\t Ви ввели символ пунктуації, спробуйте знову \n\n", S ) ;

cout<<S ; goto begin; // друк повідомлення й перехід у початок циклу

}

if ( ! isdigit ( Age [ i ] ) )    // якщо i–й символ не є цифрою

goto begin ;            // перехід у початок циклу

}

Chartooem ( "\n\t\t Ваш вік: ", S ) ;

сout << S << Age << "\n\n" ;   // друк віку

return 0 ;                                    // вихід з функції

}

}

Тут користувачеві пропонується ввести свій вік. Функція cin.getline поміщає в рядок Age уведену послідовність ( до трьох) символів, після чого виконується перевірка всіх уведених елементів масиву на приналежність до літер, escape - послідовностей або символам пунктуації. Якщо результат відповідної перевірки позитивний, користувачеві пропонується ввести дані повторно. А якщо ні, то всі введені елементи рядки перевіряються на приналежність до цифрового набору даних. Якщо хоча б один із символів не задовольняє умові, що перевіряється, цикл уведення повторюється спочатку. Після коректного введення даних на екран виводиться повідомлення про вік користувача, і програма завершує роботу.

ПОШУК СИМВОЛІВ

Одна із задач, що часто зустрічаються, при роботі з рядками – пошук окремого символу або навіть групи символів. Бібліотека string.h пропонує широкий набір стандартних функцій.

Функція strchr

Функція знаходження символу в рядку strchr має наступний прототип:

char* strchr ( const char* string, int c )

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

Нижче розглядається фрагмент, що здійснює пошук заданого символу в рядку.

char S [81] ;           // оголошення рядка з вісімдесяти символів

char* ps ;                // оголошення вказівника на рядок

Chartooem ( "Назвався U груздем, U нарікай U на U себе", S ) ;      // ініціалізація рядка

cout << S << '\n' ;   // вивід на екран вихідного рядка

ps = strchr ( S, 'U' ) ;       // повертає вказівник на перший пробіл

while ( ps )              // доти, поки вказівник ps не рівний NULL

{

ps++ ;                       // збільшення вказівника на одиницю

cout << ps << '\n' ; // вивід на екран символів від знайденого пробілу до кінця рядка

ps = strchr ( ps, ' ' ) ; // пошук наступного пробілу

}

У результаті роботи програми вказівник ps буде вказувати спочатку на початок другого слова, потім третього і т.д. На екран будуть виведені наступні рядки:

Назвався груздем, нарікай на себе

груздем, нарікай на себе

нарікай на себе

на себе

себе

Функція strrchr

Функція strrchr здійснює пошук заданого символу з кінця рядка. Вона має наступний синтаксис:

char* strrchr (const char* string, int c )

Дана функція повертає вказівник на останній символ у рядку string, що збігся із заданим символом с. Якщо символ не знайдений, вертається значення NULL.

Функція strspn

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

size_t strspn ( const char* string, const char* group)

Функція перевіряє кожний символ рядка string на відповідність кожному із символів рядка group. У результаті роботи функції вертається число символів, що збіглися.

Наступний приклад демонструє використання даної функції:

char S1 [ ] = "Завантаження параметрів БД" ;

char S2 [ ] = "Завантаження параметррррр" ;

cout << strspn ( S1, S2 ) ;

На екран буде виведене число 17, тому що символи рядка S1 і рядка S2 збігаються аж до 177й позиції. Наведена функція розрізняє регістр символів.

Функція strcspn

Функція strcspn має синтаксис:

size_t strcpn ( const char* str1, const char* str2 )

Ця функція зіставляє символи рядка str1 і str2 і повертає довжину рядка str1, що не входить в str2. Таким чином, можна визначити, у якій позиції відбувається перетинання двох символьних масивів:

char S [ ] = "abcdefghijk" ;

int index = strcspn ( str, "elf" ) ;

Змінна index одержить значення 4, тому що в цій позиції рядка мають перший загальний елемент.

Функція strpbrk

Функція strpbrk оголошена в такий спосіб:

char* strpbrk ( const char* str1, const char* str2)

Ця функція відшукує місце входження в рядок str1 кожного із символів рядка str2. Якщо символи знайдені, вертається місце першого входження будь-якого символу з str2 у рядок str1. А якщо ні, то функція повертає NULL. Нижче ілюструється використання функції strpbrk:

char S1 [ ] = "abcdefghijk" ;

char S2 [ ] = "ecb" ;

char* ps ;

ps = strpbrk ( S1, S2 ) ;

cout << ps << '\n' ;

У результаті буде виведена подстрока "bcdefghijk", тому що символ 'b' з рядка S2 зустрічається в рядку S1 раніше інших.

ПОШУК ПОДСТРОК

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

Функція strstr

Функція strstr описана в такий спосіб:

char* strstr ( const char* str, const char* substr)

Дана функція здійснює сканування рядка str і знаходить місце першого входження подстроки substr у рядок str. У випадку успішного пошуку функція strstr повертає вказівник на перший символ рядка str, починаючи з якого випливає точний збіг частини str обов'язково з усією лексемою substr. Якщо подстрока substr не знайдена в str, вертається NULL.

Наступний приклад показує використання функції strstr.

char S1 [81] ;                                                        // оголошення рядка

Chartooem ( "Проводиться пошук елемента", S1 ) ; // ініціалізація рядка

char S2 [81] ;                                                        // оголошення рядка

Chartooem ( "пошук", S2) ;                                // ініціалізація рядка

char* ps ;                                                               // оголошення вказівника на рядок

ps = strstr ( S1, S2 ) ;                                            // ініціалізація вказівника на рядок

cout << ps << '\n' ;                                                // вивід на екран "пошук елемента"

На екран буде виведено "пошук елемента", тому що подстрока, що втримується в S2, перебуває усередині рядка S1 і функція strstr установить вказівник ps на відповідний елемент символьного масиву S1.

Щоб знайти місце останнього входження подстроки в рядок, можна скористатися наступним прийманням: обидві рядки реверсируются за допомогою функції strrev, а потім отриманий результат аналізується у функції strstr.

Функція strtok

Функція strtok має синтаксис:

char* strtok ( char* str, const char* delim)

Ця функція виконує пошук у рядку str подстроки, обрамленої по обидва боки будь-яким символомдроздільником з рядка delim. У випадку успішного пошуку дана функція обрізає рядок str, поміщаючи символ '\0' у місці, де закінчується знайдена лексема. При повторному пошуку лексеми в зазначеному рядку str першим параметром слід указувати NULL. Тому що strtok модифікує рядокроригінал, рекомендується попередньо зберігати копію вихідного рядка. Наведений нижче приклад ілюструє вищесказане.

Припустимо, необхідно розбити пропозицію, наявне в строковому масиві, за словами й вивести кожне з них на екран.

char S [81] ;                         // оголошення рядка

char* ps ;                             // оголошення вказівника на рядок

char* Del="U.?!,";            // оголошення й ініціалізація вказівника на рядок,

                                              // утримуючу набір роздільників

Chartooem ("Назвався груздем, нарікай на сябя!",S) ;     // перетворення рядка

ps = strtok ( S, Del ) ;          // ініціалізація вказівника на рядок адресою першого слова

if ( ps ) cout << ps << '\n' ; // якщо вказівник існує, виводить на екран перше слово

while ( ps )                           // доти, поки вказівник існує

{

ps=strtok ( NULL, Del ) ;     // вказівник одержує адресу чергового слова

if ( ps ) cout << ps << '\n' ;   // якщо вказівник існує, виводить на екран чергове слово

}

У даній програмі оголошується підлягаюча аналізу рядок S, подстрока Del, що містить набір роздільників (Delimiters), і вказівник на символьний тип даних ps. Виклик функції strtok (S, Del) сканує рядок S і як тільки в ній зустрінеться будь-який символ, що входить у подстроку Delimiters ( у цьому випадку це символ пробілу), вказівник ps стане посилатися на початок вихідного рядка до знайденого символу. Тобто ps буде містити:

*ps = "Назвався" ;

 Завдяки тому, що функція strtok поміщає в знайденім місці нуль-термінатор ('\0'), вихідний рядок модифікується. Таким чином, масив символів S прийме значення:

"груздем, нарікай на сябя!"

Здійснивши перевірку вказівника ps на існування в операторові if ( ps ), знайдене слово виводиться на екран. Далі в циклі за допомогою функції strtok перебуває останній нуль-термінатор рядка S:

ps = strtok ( NULL, Del ) ;

що, фактично, відповідає локалізації наступного слова пропозиції, і знайдена послідовність символів виводиться на екран.

ФУНКЦІЇ ПЕРЕТВОРЕННЯ ТИПУ

Функції перетворення даних досить часто використовуються, як випливає из назви, для перетворення одного типу даних в інший тип. У наведеній нижче таблиці перераховані основні функції, їх прототипи підключаються в заголовному файлі stdlib.h.

Найменування Короткий опис
atof перетворить рядок символів у число із плаваючою крапкою
atoi перетворить рядок символів у рядок типу int
atol перетворить рядок символів у число типу long
strtod перетворить рядок символів у число із плаваючою крапкою типу double
strtol перетворить рядок символів у число типу long
strtoul перетворить рядок символів у число типу unsigned long
ecvt перетворить число із плаваючою крапкою типу double у рядок символів; десяткова крапка й знак числа не включаються в отриманий рядок; позиція крапки й знак числа вертаються окремо
fcvt ідентично ecvt, але округляє отримане значення до заданого числа цифр
gcvt перетворить число із плаваючою крапкою типу double у рядок символів, включаючи символ десяткової крапки й використовуючи специфіковане число цифр
itoa перетворить число типу int у рядок символів
ltoa перетворить число типу long у рядок символів
ultoa перетворить число типу unsigned long у рядок символів

Найчастіше, дані функції використовуються для перетворення чисел, уведених у вигляді символьних рядків, у числову представлення, а також для виконання певних арифметичних операцій над ними й зворотне перетворення в рядок символів. Розглянемо самі широко використовувані з них.

ПЕРЕТВОРЕННЯ РЯДКА В ЧИСЛО

Функції atoi і atol

Синтаксис функцій atoi і atol має вигляд:

int atoi ( const char* ptr ) ;

int atol ( const char* ptr ) ;

Ці функції перетворять Ascilz-Рядок символів, на який вказує ptr, у число типу int і long відповідно. Робота цих функцій в 32нрозрядній моделі пам'яті не відрізняється. Якщо преутворене число перевищує діапазон значень типу int, функція поверне непередбачене значення. Наприклад:

char S [41] = "400000" ; // оголошення й ініціалізація рядка

int n ;                                // оголошення змінної типу int

n = atoi ( S ) ;                   // ініціалізація змінної значенням перетвореного рядка

cout << "n=" << n << '\n' ; // виводить на екран “400000”

strcat ( S, "0000" ) ;         // додає в кінець рядка чотири нулі

long m;                             // оголошення змінної типу long

m = atoll ( S ) ;                 // ініціалізація змінної значенням перетвореного рядка

cout << "m=" << m << '\n' ; // виводить на екран “-294967296”

Функції _atoi64

Синтаксис функцій _atoi64 має вигляд:

__int64 _atoi64 ( const char* ptr ) ;

Ця функція перетворять Ascilz-Рядок символів, на який вказує ptr, у число типу __int64. Якщо преутворене число перевищує діапазон значень типу __int64, функція поверне непередбачене значення. Наприклад:

char S[41] = "7000000000" ;      // оголошення й ініціалізація рядка

__int64 h ;                       // оголошення змінної типу __int64

h = _atoi64(S) ;               // ініціалізація змінної значенням перетвореного рядка

printf ( "%I64d", h ) ;       // виводить на екран “7000000000”

Функції atof

Функція atof, певна як

double atof(const char* ptr)

виконує перетворення Asciiz-Рядка в число із плаваючою крапкою типу double. Рядок символів повинна бути представлена з урахуванням формату:

[пробіли][знак][цифри][.][цифри][е|Е[знак]цифри],

де

пробіли – послідовність пробілів або табуляторів;

знак – символ '+' або '' ;

цифри – десяткові цифри;

е|Е – символ показника ступені.

Перетворення символів припиняється, як тільки знайдений перший неконвертований символ або досягнутий кінець рядка. Приклад використання функції atof:

char S [41] = "12345e66" ; // оголошення й ініціалізація рядка

double d ;                        // оголошення змінної типу double

d = atof ( S ) ;                   // ініціалізація змінної значенням перетвореного рядка

cout << "d=" << d << '\n' ; // виводить на екран "d=1.2345e+070"

Функції strtod

Функція strtod перетворить рядок символів у число із плаваючою крапкою. Її синтаксис має такий вигляд:

double strtod ( const char *s, char **endptr) ;

Ця функція так само, як і функція atof, перетворить рядок, на який вказує s, у число типу double, з тим лише відмінністю, що у випадку припинення конвертування рядка повертає вказівник endptr на перший непреобразуемый символ. Це дозволяє організувати надалі обробку частини, що залишився, рядка. Приклад використання функції strtod:

char S [41] = "12345f66" ; // оголошення й ініціалізація рядка

double d ;                        // оголошення змінної типу double

char* Err ;                        // оголошення вказівника на рядок помилки

d = strtod ( S, &Err) ;       // ініціалізація змінної значенням перетвореного рядка

                                           // передача по вказівникові рядка помилки

cout << "d=" << d << '\n' ; // виводить на екран " d = 12345 "

cout << "Error=" << Err << '\n' ;   // виводить на екран " Error = f66 "

ПЕРЕТВОРЕННЯ ЧИСЛА В РЯДОК

Функції _itoa і _ltoa

Функції зворотного перетворення itoa і _ltoa роблять конвертування чисел типу int і long відповідно в рядок символів. Вони має наступний синтаксис:

char *_ltoa ( long value, char *string, int radix ) ;

char *_itoa ( int value, char *string, int radix ) ;

Дані функції ухвалюють як аргумент число value і перетворять його в рядок string з урахуванням підстави системи числення, представленої в змінній radix. Наступний фрагмент програми перетворить ціле число в рядок, використовуючи десятеричну систему числення:

int numb = 98765 ;

char S [10] ;

_itoa ( numb, S, 10 ) ;

cout << numb << '\n' << S ;

Функція gcvt

Функція gcvt має прототип:

char* gcvt ( double val, int ndec, char *buf ) ;

і здійснює конвертування числа val типу double в Ascliz-Рядок, поміщаючи її в буфер buf. Якщо число цифр, що підлягають перетворенню, менше цілого числа, зазначеного в ndec, у перетворенім числі вказуються символи знака й десяткової крапки, при цьому молодші розряди дробової частини відкидаються. А якщо ні, то число перетвориться в експонентну форму. Функція повертає вказівник на початок сформованого рядка.

Наступний нижче приклад демонструє використання функції gcvt для перетворення чисел, що мають різну представлення в масиви цифрових символів.

char str[10] ;

double num ;

// Значущих цифр:

int sig =4;

// Звичайне представлення числа

num = 3.547;

gcvt(num, sig, str);

cout « str « '\n' ;

// Негативне число

num = -843.7105;

gcvt(num, sig, str);

cout « str « ' \n' ;

// Експонентне представлення num = 0.135e4;

gcvt(num, sig, str) ;

cout « str « ' \n' ;

 










Последнее изменение этой страницы: 2018-06-01; просмотров: 165.

stydopedya.ru не претендует на авторское право материалов, которые вылажены, но предоставляет бесплатный доступ к ним. В случае нарушения авторского права или персональных данных напишите сюда...