Форум программистов, компьютерный форум CyberForum.ru

Разбиение произвольного текста на строки указанной длины - C++

Восстановить пароль Регистрация
Другие темы раздела
C++ обработки массивов http://www.cyberforum.ru/cpp-beginners/thread115906.html
1)Составить программу для подсчета суммы четным элементов двумерной таблицы А размером m × n. Сформировать матрицу с помощью генератора случайных чисел и организовать ее вывод на экран 2)В прямоугольном матрицы определить количество столбцов, содержащих только числа одного знака (положительные или отрицательные) и не содержащих нулевых элементов
C++ Вводятся два произвольных числа A и B. Вывести на экран, делится ли большее из них на меньшее без остатка или нет 1. Вводятся два произвольных числа A и B. Вывести на экран, делится ли большее из них на меньшее без остатка или нет. 2. Вычислить сумму с заданной точностью (суммирование производить до появления в сумме слагаемых, меньших заданной величины E): S=1+1/2+1/4+1/8+1/16+... Помогите пожалуйста код с++ http://www.cyberforum.ru/cpp-beginners/thread115883.html
C++ В массиве A из N элементов (N не больше 30) определить количество элементов, имеющих четные значения, и сумму этих элементов.
1. В массиве A из N элементов (N не больше 30) определить количество элементов, имеющих четные значения, и сумму этих элементов. Число N и значения элементов массива задаются вводом. 2. Задан массив А из 20 элементов. Поменять местами 1-й элемент с 11-м , 2-й с 12-м , 3-й с 13-м и т. д. Вывести исходный и полученный массивы. Элементы массива A должны быть случайными числами в диапазоне от 0...
Запись массива символов в файл C++
Здравствуйте! А кто знает как записать массив символов, имеющий пробелы, в файл, а потом его считать и вывести на экран? Подробнее: - нужно взять массив типа char; - заполнить его больше, чем 2 словами через пробел; - записать его в файл - прочитать эти слова из файла в тот же массив (или новый); - вывести эти слова на экран; Писать на чистом С++, т.е. используя iostream и fstream....
C++ Переход на плюсы. http://www.cyberforum.ru/cpp-beginners/thread115841.html
Здравствуйте. Я вот уже год как программирую на языке Си, и хотелось бы начать на плюсах... С ужасом обнаружил, что меня пугает даже немного "приПЛЮСнутый" код. Хотелось бы получить рекомендации по литературе, которая помогла бы сделать этот переход безболезненным (Без груды программ типа "Hello world!!!" и объяснений как пользоваться функцией printf). Заранее спасибо!
C++ Связанный список (Linked list). Добрый день. Вот пишу функцию (в коде название - smash), которая бы из текущего списка создавала 2 других: парные числа и непарные, но почему-то отказывается работать. Может кто могбы подсказать, в чем проблема? Код: struct elem { int num; elem *next; подробнее

Показать сообщение отдельно
-=ЮрА=-
Заблокирован
Автор FAQ
18.04.2010, 18:23  [ТС]     Разбиение произвольного текста на строки указанной длины
Всё таки пришлось выловить ещё пару багов, и добавить ещё одну функцию
C++
1
bool is_null_str(char * str);
В программе всё прокоменчено...Приношу извинения за 3-ю редакцию - сразу всего и не упомнишь)))
Ниже подправленный код, в файле text.txt текстовый блок который использовал для тестирования
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
#include <windows.h>
#include <stdio.h>
 
//Выделяем память под наш текстовый блок
char * str = (char *)malloc(sizeof(char));
//Выделяем память под массив строк
char ** sMass = (char **)malloc(sizeof(char));
                //ФУНКЦИИ
//Функция ввода текста до тех пор пока не встретиться символ ch_end
char * enter_text(char * str, char ch_end);
//Выделение отдельной строки длиной sLen из текстового блока sBlock
//начиная с позиции iPos
char * get_string(char * sBlock, char * str, int iPos, int sLen);
//Равномерно распределяет пробелы между словами если
//их число вконце больше nSpaces
char * div_spaces(char * sBlock, int nSpaces);
//Возвращает строку без пробелов вначале
char * skip_spaces(char * str);
//Вставляет подстроку ins в строку str с позиции iPos
char * str_insert(char * str, int iPos, char * ins);
//Проверка того что строка состоит полностью из пробелов
bool is_null_str(char * str);
 
void main()
{
    printf("\tEnter text block\r\n");
    str = enter_text(str, '\n');
    printf("\tEnter length of 1 string\r\n");
    int sLen = -1;scanf("%d",&sLen);
    int nStr = strlen(str) / sLen + 1;
    sMass = (char **)realloc(sMass,nStr*sizeof(char));
    printf("\tStrings after dividing input text\r\n");
    //Формируем массив строк sMass
    for(int i = 0,iAdd = 0; i < nStr; i++)
    {
        sMass[i] = (char *)malloc(sLen);
        sMass[i] = get_string(str, sMass[i], iAdd, sLen);
        iAdd += strlen(sMass[i]);
        printf("\t[%02d] :\r\n",i + 1);
        printf("->%s<-\r\n",sMass[i]);
        //Строка с перераспределёнными пробелами
        //Если строка полностью состоит из пробелов
        //её преобразование не производим
        printf("->%s<-\r\n",is_null_str(sMass[i]) ? sMass[i] : div_spaces(sMass[i], 3));
        //Примечание
        //Если исходные строки не нужны то можно
        //записать так sMass[i] = div_spaces(sMass[i], 3);
        if(strlen(str) <= iAdd)
            break;
    }
    printf("Num of strings : %d\r\n", (nStr = i + 1));
    printf("Press NUM1 to enter new text block\r\n");
    getchar();
    str = enter_text(str, '\n');
    if(str[0] == '1')
        main();
}
 
char * enter_text(char * str, char ch_end)
{
    int sLen = 0;
    if(str)
    {
        while((str[sLen++] = getchar()) != ch_end)
            str = (char *)realloc(str,(sLen + 1)*sizeof(char));
        str[sLen - 1] = '\0';
    }
    return str;
}
 
char * get_string(char * sBlock, char * str, int iPos, int sLen)
{
    if(sBlock != NULL && str != NULL)
    {
        for(int i = iPos; i < iPos + sLen; i++)
            str[i - iPos] = sBlock[i];
 
        //При динамическом выделении памяти
        //вконце строк идёт мусор, поэтому вконце
        //необходим терминатор '\0'!!!
        str[i - iPos] = '\0';
        //Проверяем содержит ли строка пробелы
        //При этом мы не должны учитывать пробелы
        //которые идут вначале строки перед словом
        //т.е необходимо выбросить начальные пробелы
        char * chBuf = strchr(str,' ');
        if(str[0] == ' ')
        while(*chBuf)
        {
            if(chBuf[0] != ' ')
                break;
            chBuf++;
        }
        bool IsSpaces = false;
        //Проверка данного условия необходима 
        //для случая попадания в середину слова, 
        //при этом если строка не содержит пробелов
        //т.е. состоит из 1-го слова
        //то необходимо докопировать слово в строку
        //иначе отбросить лишние символы
 
        //Зададимся строкой "строка символов"
        //Пример 1: - строка из 1 слова попали в его середину
        //пусть длина подстроки 4 символа тогда
        //
        //подстрока = "стро" - в этом случае надо докопировать
        //оставшуюсячасть слова, т.е. подстрока = "строка"!!!
        //
        //Пример 2: - строка из 2 слов попали в символы 2-го
        //пусть длина подстроки 8 символов тогда
        //
        //подстрока = "строка с" - в этом случае надо отступить
        //назад до пробела, т.е. подстрока = "строка"!!!
        if(*chBuf)
        if(strchr(chBuf,' '))
            IsSpaces = true;
        
        //Если строка оканчивается посередине слова, 
        //то отбрасываем слово, путём сдвига обратно
        //одновременно уменьшая длину строки
        while(*(sBlock + i))
        {
            str = (char *)realloc(str,i - iPos + 1);
            str[i - iPos] = sBlock[i];
            if(sBlock[i] == ' ')
                break;
            if(IsSpaces)
                i--;
            else
                i++;
        }
        str[i - iPos] = '\0';
    }
    return str;
}
 
char * div_spaces(char * sBlock, int nSpaces)
{
    if(sBlock != NULL)
    {
        int nCount = 0,sLen = strlen(sBlock);
        char * chBuf = strrchr(sBlock,' ');
        //Вычисляем число пробелов вконце
        //для этого находим последний пробел в строке
        //и последовательно отступаем на символ назад
        //до того как предыдущий символ станет не пробелом
        if(chBuf)
        {
            //Также необходимо учесть что последний пробел должен
            //также являться последним символом строки!!!
            //В противном случае мы будем подсчитывать количество
            //пробелов в каком нибудь промежутке в середине слова
            if(strlen(chBuf) == 1)
            while((chBuf - nCount) != NULL)
            {
                nCount++;
                if(*(chBuf - nCount) != ' ')
                    break;
            }
        }
        if(nSpaces < nCount)
        {
            int nBlocks = 0;
            int *sPos = (int *)malloc(sizeof(int));
            chBuf = skip_spaces(sBlock);
            while(chBuf != NULL)
            {
                //Записываем в массив позиции промежутков между словами
                sPos[nBlocks] = strlen(sBlock) - strlen(chBuf);
                if(chBuf = skip_spaces(chBuf + sPos[nBlocks]))
                    chBuf = strchr(chBuf,' ');
                //Переставил nBlocks++; т.к. в случае досрочного выхода
                //из цикла операция инкремента не выполнялась nBlocks++
                //в результате возникали ситуации когда nBlocks = 0
                //и при выходе из цикла в выражении nAdd = (nCount - nSpaces)/nBlocks
                //было деление на нуль, что вызывало ошибку
                nBlocks++;
                if(chBuf == NULL)
                    break;
                sPos = (int *)realloc
                (
                    (void *)sPos,
                    (nBlocks + 1)*sizeof(int)
                );
            }
            int nAdd = (nCount - nSpaces)/nBlocks;
            //Если пробелов вконце строки не хватает для добавления
            //во все промежутки между слвами, например слов 5 а
            //лишних пробелов от 1-го до 5-ти
            if(nAdd < 1)
            {
                while(nAdd < 1)
                {
                    nBlocks--;
                    //Это случай нескольких слов в строке и всего
                    //1-го лишнего пробела вконце
                    if(nBlocks == 0)
                    {
                        nAdd = (nCount - nSpaces);
                        break;
                    }
                    nAdd = (nCount - nSpaces)/nBlocks;
                }
                nBlocks = nAdd/(nCount - nSpaces);
            }
            //Случай всего 1-го слова в строке, в этом случае удваиваем
            //nAdd и данные проблеы добавляем с позиции sPos[0], т.е перед словом
            if(nBlocks == 2 && is_null_str(sBlock + sPos[nBlocks - 1] + 1))
            {
                nAdd    *= 2;
                nBlocks--;
            }
            while(0 < nBlocks)
            {
                nBlocks--;
                sBlock = str_insert
                (
                    sBlock,
                    sPos[nBlocks],
                    &sBlock[strlen(sBlock) - nAdd]
                );
                //Обрезаем строку, т.к. нам необходима лишь 
                //перестановка внутри sBlock, т.е
                //Например :
                //sBlock = "строка12", необходимо переставить подстроку "12"
                //на позицию 0
                //после str_insert получаем вставку "12" в, т.е sBlock = "12строка12", 
                //для перестановки необходимо убрать символы "12" вконце строки
                sBlock[sLen] = '\0';
            }
            free((void *)sPos);
        }
    }
    return sBlock;
}
 
char * skip_spaces(char * str)
{
    int i = 0;
    if(str != NULL)
    {
        while((str + i) != NULL)
        {
            if(str[i] != ' ')
                break;
            i++;
        }
    }
    return (str + i);
}
 
char * str_insert(char * str, int iPos, char * ins)
{
    if(*str && *ins)
    {
        int sLen = strlen(str);
        int nAdd = strlen(ins);
        //В случае перекрывания элементов строк str и ins
        //при перестановке символов внутри str возможно
        //изменение символов ins!!!
        //Например :
        //строка12, необходимо переставить подстроку "12"
        //на позицию 0, тогда после цикла 
        //  for(i = sLen + nAdd - 1; iPos + nAdd <= i; i--)
        //произойдёт следующее :
        //str = "стстрока"
        //ins = "ка" 
        //для избежания этого вводим дополнительную строку sIns
        /////////////////////////////////////////////////////////
        char * sIns = (char *)malloc(nAdd);
        for(int i = 0;i < nAdd; i++)
            sIns[i] = ins[i];
        /////////////////////////////////////////////////////////
        if(iPos < sLen)
        {
            str = (char *)realloc(str,sLen + nAdd);
            for(i = sLen + nAdd - 1; iPos + nAdd <= i; i--)
                str[i] = str[i - nAdd];
            for(i = iPos; i < iPos + nAdd;i++)
                str[i] = sIns[i - iPos];
        }
        //////////////////////////////////////////////////////////
        free(sIns);
        //////////////////////////////////////////////////////////
    }
    return str;
}
 
bool is_null_str(char * str)
{
    bool RetVal = true;
    if(str != NULL)
    {
        int sLen = strlen(str);
        for(int i = 0; i < sLen; i++)
            if(str[i] != ' ')
                RetVal = false;
    }
    return RetVal;
}
Миниатюры
Разбиение произвольного текста на строки указанной длины  
Вложения
Тип файла: txt text.txt (1.1 Кб, 19 просмотров)
 
Текущее время: 07:24. Часовой пояс GMT +3.
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2016, vBulletin Solutions, Inc.
Рейтинг@Mail.ru