![]() |
|
Модераторы: Daevaorn |
![]()
|
|
| chubaka |
|
|||
|
Шустрый ![]() Профиль Группа: Участник Сообщений: 55 Регистрация: 8.6.2007 Репутация: нет Всего: нет |
Есть обьект std::string string1, содержащий русские символы. Нужно узнать, присутствует ли в нем строка std::string string2, тоже содержащая русские символы.
С strstr не получается. Как можна решить задачу максимально просто ? Это сообщение отредактировал(а) chubaka - 26.3.2008, 07:03 |
|||
|
||||
| korian |
|
|||
|
Опытный ![]() ![]() Профиль Группа: Участник Сообщений: 651 Регистрация: 8.3.2008 Где: Украина, Харьков Репутация: 3 Всего: 17 |
для utf-8 вот это:
unsigned char * _mbsstr(const unsigned char *s1, const unsigned char *s2); Это сообщение отредактировал(а) korian - 26.3.2008, 10:17 |
|||
|
||||
| chubaka |
|
|||
|
Шустрый ![]() Профиль Группа: Участник Сообщений: 55 Регистрация: 8.6.2007 Репутация: нет Всего: нет |
Компилятор gcc, система unix.
mbstring.h не нашел у себя |
|||
|
||||
| Dennnis |
|
|||
![]() Шустрый ![]() Профиль Группа: Участник Сообщений: 145 Регистрация: 23.3.2008 Репутация: нет Всего: 4 |
int pos = (int)string1.find(string2.c_str());
if(pos == -1) { //не нашел } --------------------
Get Rich or Die Tryin' |
|||
|
||||
| korian |
|
|||
|
Опытный ![]() ![]() Профиль Группа: Участник Сообщений: 651 Регистрация: 8.3.2008 Где: Украина, Харьков Репутация: 3 Всего: 17 |
||||
|
||||
| chubaka |
|
|||
|
Шустрый ![]() Профиль Группа: Участник Сообщений: 55 Регистрация: 8.6.2007 Репутация: нет Всего: нет |
korian, именно. find,strstr не работают
|
|||
|
||||
| korian |
|
|||
|
Опытный ![]() ![]() Профиль Группа: Участник Сообщений: 651 Регистрация: 8.3.2008 Где: Украина, Харьков Репутация: 3 Всего: 17 |
если у вас нету функции:
unsigned char * _mbsstr(const unsigned char *s1, const unsigned char *s2); я даже хз, что тут посоветовать... имху переходить в ASCII или в UNICODE |
|||
|
||||
| chubaka |
|
|||
|
Шустрый ![]() Профиль Группа: Участник Сообщений: 55 Регистрация: 8.6.2007 Репутация: нет Всего: нет |
Немного конкретизировал задачу. Перегнал данные в wchar_t, но всеравно не ищет. Код:
|
|||
|
||||
| bsa |
|
|||
![]() Эксперт ![]() ![]() ![]() ![]() Профиль Группа: Модератор Сообщений: 9185 Регистрация: 6.4.2006 Где: Москва, Россия Репутация: 63 Всего: 196 |
А может вместо std::string спользовать std::wstring? С ним все работает.
|
|||
|
||||
| korian |
|
|||
|
Опытный ![]() ![]() Профиль Группа: Участник Сообщений: 651 Регистрация: 8.3.2008 Где: Украина, Харьков Репутация: 3 Всего: 17 |
а эта функция (mbstowcs) нули сама не ставит? если у вас limit_string и search_for это объекты std::string'а, то length() для них вычисляется не правильно. и если надо записывать нули, то надо указывать вайдовский ноль: w_limit_string[<я хз как длину определить>] = L'\0'; Добавлено @ 13:49 почитал про mbstowcs... попробуйте так:
Это сообщение отредактировал(а) korian - 26.3.2008, 13:51 |
|||
|
||||
| chubaka |
|
|||
|
Шустрый ![]() Профиль Группа: Участник Сообщений: 55 Регистрация: 8.6.2007 Репутация: нет Всего: нет |
korian, на счет нулей - не знаю, просто перестраховался. Пробовал и так и так.
На счет длины - вы не правы. Да, char[5] и wchar_t[5] занимают разное количество памяти, но длина текста у них аналогичная. В первом случае каждый символ - 8 бит, во втором - 16. Добавлено через 2 минуты и 12 секунд Уверяю вас, дело не в длине. Я проверял вручную переменные которые образовались, значения у них - правильные. Это сообщение отредактировал(а) chubaka - 26.3.2008, 13:50 |
|||
|
||||
| korian |
|
|||
|
Опытный ![]() ![]() Профиль Группа: Участник Сообщений: 651 Регистрация: 8.3.2008 Где: Украина, Харьков Репутация: 3 Всего: 17 |
прав ASCII - для символа 8 бит UTF-8 (он же мультибайт) - длина символа 8 бит или 16 бит UTF-16 (он же UNICODE, wchar_t) - длина символа 16 бит. если использовать функцию ASCII (strlen) для UTF-8, то результат не предсказуем... хотя может и предсказуем, если знать кодирование в UTF-8, я его не знаю. если в UTF-8 возможет вариант, что один символ записывается как \0xAB\0x00, тогда strlen будет возвращать значение меньше истинной длины. а в общем случае, если такого варианта не может быть, то strlen будет возвращать длину больше реальной. Это сообщение отредактировал(а) korian - 26.3.2008, 13:56 |
|||
|
||||
| chubaka |
|
|||
|
Шустрый ![]() Профиль Группа: Участник Сообщений: 55 Регистрация: 8.6.2007 Репутация: нет Всего: нет |
korian, понял =) спасибо )
По поводу вашего примера - _mbslen (также как и _mbsstr, выше писал) - у меня ведь ее нет =)) была бы, я думаю давно решил бы проблему перегоном в unsigned char. Где найти mbstring.h и библиотеку для него ? FreeBDS. |
|||
|
||||
| korian |
|
|||
|
Опытный ![]() ![]() Профиль Группа: Участник Сообщений: 651 Регистрация: 8.3.2008 Где: Украина, Харьков Репутация: 3 Всего: 17 |
тогда посмотрите значения w_limit_string_const и w_search_for_const
они нормальные? если да, то что-то уж очень все странно... |
|||
|
||||
| chubaka |
|
|||
|
Шустрый ![]() Профиль Группа: Участник Сообщений: 55 Регистрация: 8.6.2007 Репутация: нет Всего: нет |
korian, да, нормальные. Но русский в w_limit_string_const - кракозябрами, а в w_search_for_const - нормальный. Хочу перегнать в unsigned char, но нужна _mbsstr.
|
|||
|
||||
| korian |
|
|||
|
Опытный ![]() ![]() Профиль Группа: Участник Сообщений: 651 Регистрация: 8.3.2008 Где: Украина, Харьков Репутация: 3 Всего: 17 |
а такая функция есть? - mblen
|
|||
|
||||
| chubaka |
|
|||
|
Шустрый ![]() Профиль Группа: Участник Сообщений: 55 Регистрация: 8.6.2007 Репутация: нет Всего: нет |
Да. Попробую с ней
Это сообщение отредактировал(а) chubaka - 26.3.2008, 14:12 |
|||
|
||||
| marcusmae |
|
||||||||||||||
![]() stravaganza ![]() ![]() Профиль Группа: Участник Сообщений: 874 Регистрация: 26.3.2006 Репутация: 5 Всего: 39 |
Имхо, максимально просто - это прекратить рассматривать мультибайтовые чары и перейти к их представлению, как указатели на байтовые массивы. Сначала нам нужна функция, которая будет в массиве байт находить по эталону два последовательных байта (два байта - это, по определению, представление для кириллицы в utf-8).
Далее, нужна функция, которая будет в массиве байт находить эталонную последовательность пар байт.
Ключевая функция - memcmp - сравнение байтовых последовательностей. Для проверки, строки я ввожу из файлов в формате UTF-8 : string.txt
substring.txt
Файлы - в UTF-8, но читаю, как байты :
В результате, для приведённых файлов
ответом является
то есть, коричневая лисица началась с десятой позиции в строке. В примечание - utfHeaderOffset - некий маркер utf-формата, который можно отладчиком увидеть в обоих строках. Мы должны его перепрыгнуть, иначе совпадений не будет найдено (-1). Вроде не очень сложно, да?.. Это сообщение отредактировал(а) marcusmae - 26.3.2008, 15:18 Присоединённый файл ( Кол-во скачиваний: 4 )
CyrUTF8.rar 179,63 Kb-------------------- ἀπὸ μηχανῆς θεός |
||||||||||||||
|
|||||||||||||||
| chubaka |
|
|||
|
Шустрый ![]() Профиль Группа: Участник Сообщений: 55 Регистрация: 8.6.2007 Репутация: нет Всего: нет |
marcusmae, спасибо огромное за такой полный ответ, но мне не помогло.
Исходная задача такая: есть 2 std::string обьекта. Они не загружаются из файла. Они через сокеты получают данные от другого сервера. Отсюда видимо значит что и маркера UTF формата не будет. Это сообщение отредактировал(а) chubaka - 27.3.2008, 09:00 |
|||
|
||||
| korian |
|
|||
|
Опытный ![]() ![]() Профиль Группа: Участник Сообщений: 651 Регистрация: 8.3.2008 Где: Украина, Харьков Репутация: 3 Всего: 17 |
про маркеры никто ничего не говорил. короче я так понимаю, что проблема у вас в том, что вы или не знаете форматов сравниваемых строк, или не правильно их задаете. поясните от куда берется строка limit_string и как задается search_for. и в каком они формате и уверены ли вы, что они в этом формате. Это сообщение отредактировал(а) korian - 27.3.2008, 09:38 |
|||
|
||||
| chubaka |
|
|||
|
Шустрый ![]() Профиль Группа: Участник Сообщений: 55 Регистрация: 8.6.2007 Репутация: нет Всего: нет |
korian, про маркеры писал ув. marcusmae.
limit_string - HTML страница, полученная CURL'ом. search_for - данные из файла, для поиска в коде HTML страницы. Загружается ifstream'ом. |
|||
|
||||
| korian |
|
|||
|
Опытный ![]() ![]() Профиль Группа: Участник Сообщений: 651 Регистрация: 8.3.2008 Где: Украина, Харьков Репутация: 3 Всего: 17 |
он писал что его надо перепрыгнуть, т.к. он нам нафиг не нужен, т.к. мы из начально знаем что там UTF-8. а по стандарту он туда пишется. если файл из которого читается search_for - UTF-8 и search_for - это std::string, а ifstream - это std::ifstream, и читается оно по типу ifstream.getline(search_for), то у вас из начально не правильные значение в search_for. Это сообщение отредактировал(а) korian - 27.3.2008, 09:59 |
|||
|
||||
| Rififi |
|
|||
|
Эксперт ![]() ![]() ![]() Профиль Группа: Завсегдатай Сообщений: 1254 Регистрация: 9.3.2008 Репутация: 11 Всего: 36 |
chubaka,
C/C++ рантайм не поддерживает работу с utf-8. поэтому перед использованием текст надо перекодировать в честный utf-16 и юзать W-функции см. MultiByteToWideChar |
|||
|
||||
| chubaka |
|
|||
|
Шустрый ![]() Профиль Группа: Участник Сообщений: 55 Регистрация: 8.6.2007 Репутация: нет Всего: нет |
korian, уважаемый, вы гений =) Огромное спасибо. Действительна проблема была в том, что я неверно вводил данные в файл. Я программирую на удаленном сервере через SSH, и клиент PuTTy неверно принимал русские символы. Спасибо большое !
Также спасибо большое всем кто старался помочь. Много полезных советов на будущее |
|||
|
||||
![]()
|
| Правила форума "С++:Общие вопросы" | |
|
|
Добро пожаловать!
Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, Earnest Daevaorn |
| 0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей) | |
| 0 Пользователей: | |
| « Предыдущая тема | C/C++: Общие вопросы | Следующая тема » |
|
|
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности Powered by Invision Power Board(R) 1.3 © 2003 IPS, Inc. |