Символьная строка, способы ее представления
Урок 13.
Тема: «Указатели и строки»
1. Представление строки.
В Си строка определяется, как набор символов, заканчивающийся символом ‘\0’, заключенная в двойные кавычки (не апострофы)
Определить строку можно следующими способами:
1) char CH[10]; // массив из 10-ти символов
2) char STR[ ] = “ABCD” // массив из 5-ти символов, 5-ый ‘\0’ автоматически
3) char strokа [4] = {‘S’,’I’,’C’,’\0’}; // при инициализации списком символьный массив приобретает статус строки, если явно в конце записать символ ‘\0’
4) char *car1 = “строка 1”; // автоматически
5) char *car2 = {“строка 2”}; // прибавляется
6) char *car3 = (“строка 3”); // символ конца строки ’\0’
7) char *car4; // не инициализированный указатель.
Явная инициализация строки (2,3,4,5,6) разрешена только при определении.
Во всех случаях CH, STR, stroka, car1, car2, car3, car4 – адреса первого символа строки.
Доступ к элементам строки можно получить двумя способами:
1. [ ] – индексация,
2. * - по адресу.
В Си индексация элементов массива ведется с 0. это соглашение языка становиться очевидным, если учесть, что индекс определяет не номер элемента, а его смещение относительно начала массива.
Например, в примере (3) массив stroka состоит из 4 элементов, тогда
stroka [0] = ‘S’, strokа [1] = ‘I’, stroka [2] = ‘C’, stroka [3] = ‘\0’
Доступ к элементам строки:
Для примера (4).
*car – это символ ‘с’ и car [0] - это символ ‘с’
*(car+2) - это символ ‘р’ и car [2]- это символ ‘р’
2. Пример программы перебора элементов строки.
//prim5.cpp – чтение элементов строки
#include <stdio.h>
#include <conio.h>
void main()
{
char *str;
cout << “Введите строку символов. \n”;
gets (str); // считывает строку из stdin и записывает адреса str, добавляя символ ‘\0’
while (*str != ‘\0’ ) // пока не конец строки
{
putch(*str);
str++; //Увеличение адреса на одну ячейку типа char
}
putch(‘\n’);
int count = 0;
while (str[count] !=’\0’) // пока не конец строки
{
putch (str [count]);
count ++;
}
putch(‘\n’);
}
При вводе строки “Компилятор языка.”
Результат:
Компилятор строки.
Компилятор строки.
В первом while (*str != ‘\0’)
{…
str++;
}
Операторы можно объединить и записывать:
while (*str++ != ‘\0’) {…}
3. Снятие игнорирования символов «пробел», «табуляция» для обеспечения ввода строки с пробелами
Если считывать строку в массив символов, то поток ввода закончится на первом встретившемся во вводе пробеле. Например:
…
char name[30];
cin>>name;
cout<<mane
…
Если в этой программе ввести предложение «Флаги нужны всем!», то результатом будет одно слово «Флаги».
Чтобы разделители «пробел» и «табуляция» тоже считывались, необходимо отменить игнорирование разделителей и считывать все символы по одному. Для этого необходимо снять флагskipw, установленный по умолчанию, выполнив следующее:
cin>>resetiosflags(ios::skipws);
Пример:
…
void main()
{
char name[30];
cin>>resetiosflags(ios::skipws);
for(int i=0;I<29;i++)
{
cin>>name[i];
if(name[i]==enter) break; //если нажали клавишу Enter, то ввод прекратить
}
name[i]=’\0’;
cout<<name;
}
Если в этой программе ввести предложение «Флаги нужны всем!», то результатом будет «Флаги нужны всем».
В приведенном примере снятие флага «Игнорировать разделители в потоке ввода» выполняется в главной функции. Лучше это делать в отдельной функции, а затем вызывать ее на выполнение.
Пример:
#include “stdafx.h”
// функция игнорирования разделителей
void string (char *string)
{
cin>> resetiosflags(ios::skipws);
for(int i=0;I<80;i++)
{
cin>>string[i];
if(string[i]= =10) break; //если нажали клавишу Enter, то ввод прекратить
}
string[i]=’\0’;
}
// главная функция
int main (int argc, char* argv[] )
{
char *str1;
str1=new(char);
cout<<”введи строку\n”;
string(str1);
while (str1 !=’\0) // пока не конец строки
{
cout<<*str1;
str1++;
}
cout<<”\n”;
return 0;
}