Форум программистов, компьютерный форум, киберфорум
С++ для начинающих
Войти
Регистрация
Восстановить пароль
Карта форума Темы раздела Блоги Сообщество Поиск Заказать работу  
 
 
Рейтинг 4.56/9: Рейтинг темы: голосов - 9, средняя оценка - 4.56
1373 / 596 / 199
Регистрация: 02.08.2011
Сообщений: 2,882
1

Стандарт языка, работа со строками. Малая русская я

04.05.2015, 02:27. Показов 1695. Ответов 22
Метки нет (Все метки)

Author24 — интернет-сервис помощи студентам
В общем помогите разобраться с локалями.

Не нужно мне про toupper и другие костыли. Только локали.

if (isalpha('я')) cout<<"\OK";

DrOffset,
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
#include <iostream>
#include <clocale>
#include <locale>
#include <cctype>
 
 
int main(int argc, char * argv[])
{
    std::locale loc(".1251");
 
    char s[] = "Фяя7яЯф02022";
 
    for (size_t i = 0, len = std::strlen(s); i < len; ++i)
    {
        if (std::isalpha(s[i], loc))
            std::cout << i << "-char is alpha" << std::endl;
    }
}
Самоубился этот код.

Добавлено через 2 минуты
И еще, считается ли русская "я" видимым символом, согласно стандарту, если она выводится в консольное окошко как символ "я" (задана в исходном коде).

Добавлено через 5 минут
Мои привычные стандарты:
для VS
setconsole(LC_ALL,"");

для mingw
setlocale(LC_ALL,"");
SetConsoleCP(1251);
SetConsoleOutputCP(1251);
______
Обычно с русским проблем не было, вводил, выводил, обрабатывал, но вот появилась малая русская "я", которая работает по особому.
0
Лучшие ответы (1)
Programming
Эксперт
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
04.05.2015, 02:27
Ответы с готовыми решениями:

Стандарт языка С++
Можно ли данный документ считать стандартом языка С++?

Стандарт языка с++ в С++ Builder
Как узнать стандарт используемого языка в C++ Builder и есть ли возможность его переключения? У...

Модули и стандарт языка
Были ли модули unit в стандарте Паскаля, или это заслуга Turbo? Ведь ООП расширение стандарта есть,...

Что такое стандарт языка, к примеру ANSI?
Я так понимаю стандарт языка содержит в себе библиотеки, созданные ANSI. Так ли это? Для чего это...

22
18843 / 9842 / 2408
Регистрация: 30.01.2014
Сообщений: 17,284
04.05.2015, 02:31 2
Цитата Сообщение от daslex Посмотреть сообщение
DrOffset, У меня этот код вылетел нафиг в gcc. Не так уж и прекрасно.
Опять же, потому что, нужно понимать что такое локаль.
Нельзя уделить теме пару минут, а потом делать на основе этого далеко идущие выводы.
Имена, которые мы передаем в конструктор локали - платформозависимы, поэтому нет гарантий, что код, который я привел для VS - сработает в mingw.
0
1373 / 596 / 199
Регистрация: 02.08.2011
Сообщений: 2,882
04.05.2015, 02:32  [ТС] 3
DrOffset, ответьте мне на вот это
Цитата Сообщение от daslex Посмотреть сообщение
считается ли русская "я" видимым символом, согласно стандарту, если она выводится в консольное окошко как символ "я" (задана в исходном коде).
0
18843 / 9842 / 2408
Регистрация: 30.01.2014
Сообщений: 17,284
04.05.2015, 02:33 4
Цитата Сообщение от daslex Посмотреть сообщение
И еще, считается ли русская "я" видимым символом, согласно стандарту, если она выводится в консольное окошко как символ "я" (задана в исходном коде).
Согласно какому стандарту? С++? С++ не определяет стандарты для символов.
Но С++ определяет понятие локаль (locale), которое регулирует работу вышеупомянутых функций. В справке об этом тоже написано.
0
1373 / 596 / 199
Регистрация: 02.08.2011
Сообщений: 2,882
04.05.2015, 02:38  [ТС] 5
Т.е. если у меня ввод русских символов работает корректно, вывод русских символов работает корректно, обработка русских символов на 99,9% работает хорошо, а в 0,1% попадает 1 символ, я, значит в локалях ковыряться должен и во всем они виноваты?

Добавлено через 2 минуты
Для некоторых определяет. Не надо мне тут, я мучался что-то в стандарте понять. Там нет русских, но символы он определяет, он определяет несколько разных множеств символов. (буква, знак пунктуации, видимые и невидимые символы, цифра)
0
18843 / 9842 / 2408
Регистрация: 30.01.2014
Сообщений: 17,284
04.05.2015, 02:42 6
Цитата Сообщение от daslex Посмотреть сообщение
Т.е. если у меня ввод русских символов работает корректно, вывод русских символов работает корректно, обработка русских символов на 99,9% работает хорошо, а в 0,1% попадает 1 символ, я, значит в локалях ковыряться должен и во всем они виноваты?
Ты должен понимать что ты делаешь, в любом случае.
Ты должен понимать работу функций, которые ты используешь.
Ты должен уметь остановиться и хорошо подумать, и, если нужно, провести исследование непонятного вопроса.
Что еще тебе сказать на это?

Добавлено через 1 минуту
Цитата Сообщение от daslex Посмотреть сообщение
Не надо мне тут, я мучался что-то в стандарте понять. Там нет русских, но символы он определяет, он определяет несколько разных множеств символов. (буква, знак пунктуации, видимые и невидимые символы, цифра)
Вот именно - множества, категории. Это абстракции. Конкретные символы определяют совсем другие стандарты.
0
1373 / 596 / 199
Регистрация: 02.08.2011
Сообщений: 2,882
04.05.2015, 02:46  [ТС] 7
Входит ли видимый символ, который отображается на экране в категорию "видимый символ", согласно стандарту?

Добавлено через 2 минуты
Или стандарт с логикой не дружит?
0
18843 / 9842 / 2408
Регистрация: 30.01.2014
Сообщений: 17,284
04.05.2015, 02:50 8
Цитата Сообщение от daslex Посмотреть сообщение
Входит ли видимый символ, который отображается на экране в категорию "видимый символ", согласно стандарту?
Нет. В такой постановке вопроса - нет.
Понятие "видимый символ" неотрывно связано с понятием "кодировка".
Ты сейчас работаешь с кодировкой 1251. Сменишь кодировку например на KOI8-R, и видимые символы будут иметь уже совсем другие коды. Именно поэтому такие функции, которые сравнивают или модифицируют символы, должны иметь представление в какой кодировке мы работаем. Иначе просто нельзя.
Ты же не думаешь, что 1251 единственная русская кодировка на свете, или что все кодировки для всех языков мира должны быть явно учтены в стандарте С++?
0
1373 / 596 / 199
Регистрация: 02.08.2011
Сообщений: 2,882
04.05.2015, 03:10  [ТС] 9
Ну я только 2 знаю
866 dos и 1251 для WIndows (у Windows)/ Это не суть.

Подозреваю, что при любой кодировке эффект будет 1 и тот же.
Ну и скакой локалью мне работать c isalpha в MinGW, если у меня программа работает в Windows1251 , а локаль 1251 для isalpha не подходит

Добавлено через 11 минут
Вот эта конструкция
C++
1
if (isalpha('я',(std::locale(".1251"))))
из-за std::locale аварийно завершает программу. Как же мне заставит работать функцию в нужной мне кодировке?
0
18843 / 9842 / 2408
Регистрация: 30.01.2014
Сообщений: 17,284
04.05.2015, 03:17 10
Цитата Сообщение от daslex Посмотреть сообщение
Ну и скакой локалью мне работать c isalpha в MinGW, если у меня программа работает в Windows1251 , а локаль 1251 для isalpha не подходит
В mingw c поддержкой системных локалей всегда было все печально, и вряд ли это в скором будущем изменится. В VS этот код будет работать правильно.
Можно написать свой вариант локали с использованием API windows. Это будет в рамках стандартного подхода, по крайней мере.
Хотя правильный способ - это вообще не использовать однобайтные кодировки в windows. Это анахронизм, и суета с локалями только одна из проблем в этом случае.
Вся windows давно уже юникодная изнутри, кодировка юникода UTF-16/UCS-2. Вот именно это и нужно использовать при написании приложения, в котором используется больше одного языка сразу.

Добавлено через 52 секунды
Цитата Сообщение от daslex Посмотреть сообщение
из-за std::locale аварийно завершает программу
Там кидается исключение, сообщающее о том, что имя переданное в конструктор, не поддерживается. Это не креш. А результат непойманного исключения.

Добавлено через 2 минуты
daslex, вот неплохой материал по теме.
0
lss
941 / 869 / 355
Регистрация: 10.10.2012
Сообщений: 2,706
04.05.2015, 03:26 11
Цитата Сообщение от daslex Посмотреть сообщение
Как же мне заставит работать функцию в нужной мне кодировке?
Не пойму, в чём проблема? Так не работает? Или что нужно?
C++
1
2
if (isalpha('я'))
    out<<"OK";
Добавлено через 5 минут
Вернее, так нужно:
C++
1
2
if (isalpha((unsigned char)'я'))
        cout<<"OK";
1
18843 / 9842 / 2408
Регистрация: 30.01.2014
Сообщений: 17,284
04.05.2015, 03:29 12
Цитата Сообщение от lss Посмотреть сообщение
Не пойму, в чём проблема? Так не работает? Или что нужно?
В определенных ситуациях так не работает.
Человек пытался выяснить, можно ли винить компилятор в том, что оно не работает.
Я пытался донести две мысли:
1) Стандарт С++ не обязывает делать поддержку всех языков мира. А только вводит правила, чтобы эту поддержку можно было сделать. Но это не является прямым требованием. Ответственность ложится на конкретную реализацию. Винить реализацию в несоответствии стандарту здесь нельзя.
2) На самом деле оно может работать, но из-за несоответствия кодировок или\и выбранной локали может выдаваться отличный от ожидаемого результат.
1
lss
941 / 869 / 355
Регистрация: 10.10.2012
Сообщений: 2,706
04.05.2015, 03:33 13
Цитата Сообщение от DrOffset Посмотреть сообщение
В определенных ситуациях так не работает.
Понятно. У ТС, такая конструкция, где конкретно не работает?
0
18843 / 9842 / 2408
Регистрация: 30.01.2014
Сообщений: 17,284
04.05.2015, 03:33 14
Цитата Сообщение от lss Посмотреть сообщение
Вернее, так нужно:
Это кстати ценное замечание. Именно в этом кроется причина проблем у ТС (знаковый бит char сохраняется в разряде знака при касте к int и мы получаем другое число).
0
1373 / 596 / 199
Регистрация: 02.08.2011
Сообщений: 2,882
04.05.2015, 03:34  [ТС] 15
Ясно. Ну со стандартом убедили. Никто ничего не нарушает
Буду знать, что функциям в VS надо кодировку указывать, а в mingw не укажешь без костылей.

Да мне оно не сильно надо. Просто в форум кинешь решение, а там: "А у меня не работает" только из-за того что, например компилятор mingw, не советовать же ему сразу на VS садиться, хотя бы и потому что потом кто-то упрямо настоит на пересадку на mingw и так гонять его по кругу и будут.
А переписывать решение не всегда желание.

Да и моменты такие не сразу и заметно ведь. Фигово, короче, всё.
0
18843 / 9842 / 2408
Регистрация: 30.01.2014
Сообщений: 17,284
04.05.2015, 03:37 16
Цитата Сообщение от lss Посмотреть сообщение
Понятно. У ТС, такая конструкция, где конкретно не работает?
Если использовать сишные локали и сишный isalpha, то каст signed char к int портит число, а локаль, даже заданная правильно, не способна это распознать. В итоге получаем неверное поведение.
В С++ реализации isalpha это учитывается посредством шаблона, и локаль применяемая к ней дает верный результат. Шаблонная реализация isalpha в mingw присутствует, а вот с std::locale - проблема, нет поддержки системного богатства.
0
1373 / 596 / 199
Регистрация: 02.08.2011
Сообщений: 2,882
04.05.2015, 03:38  [ТС] 17
Цитата Сообщение от lss Посмотреть сообщение
Вернее, так нужно:
toupper буков меньше)
0
lss
941 / 869 / 355
Регистрация: 10.10.2012
Сообщений: 2,706
04.05.2015, 03:44 18
Лучший ответ Сообщение было отмечено daslex как решение

Решение

Цитата Сообщение от DrOffset Посмотреть сообщение
Это кстати ценное замечание. Именно в этом кроется причина проблем у ТС (знаковый бит сохраняется в разряде знака при касте к int и мы получаем другое число).
Тут приводили цитату из стандарта, что для функций cctype нужен параметр unsigned char, иначе UB.

Добавлено через 3 минуты
...
The header <ctype.h> declares several functions useful for classifying and mapping characters. In all cases the argument is an int, the value of which shall be representable as an unsigned char or shall equal the value of the macro EOF. If the argument has any other value, the behavior is undefined.
2
1373 / 596 / 199
Регистрация: 02.08.2011
Сообщений: 2,882
04.05.2015, 03:44  [ТС] 19
Все у меня работает

Просто не видел я про cctype, а стандарт мне тяжело понимать.

Спасибо, что разрулили вопрос.
0
18843 / 9842 / 2408
Регистрация: 30.01.2014
Сообщений: 17,284
04.05.2015, 03:46 20
Цитата Сообщение от lss Посмотреть сообщение
Тут приводили цитату из стандарта, что для функций cctype нужен параметр unsigned char, иначе UB.
Да это понятно. Я об этом и говорю. Это из-за того, что они принимают int.
Но С++ варианты isalpha находятся в <locale> и для них такого требования нет.
Но вообще изначально речь шла не об этом слегка. Это детали реализации все.
Речь шла о концептуальной поддержке русского языка (и других) в стандарте С++. И является ли отсутствие такой поддержки нарушением со стороны разработчиков.
2
04.05.2015, 03:46
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
04.05.2015, 03:46
Помогаю со студенческими работами здесь

Раздельная компиляция и стандарт 2011 года языка Си++
Добрый день! Передо мной стоит следующая задача. Есть ПК с двумя компиляторами разных версий....

Какой стандарт языка Си лучше изучать в 2019 году? C89 или C99?
Ответвление темы https://www.cyberforum.ru/c-beginners/thread2529347.html Попытался собрать...

Работа со строками, заполнить компоненты строками из файла
Привет! Нужна помощь в заполнении формы В общем, есть форма отправки письма. У нее есть 2 функции,...

Работа со строками. Функции работы со строками
Дана строка символов. В заданном тексте определить позицию первой точки ‘ . ‘.


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
20
Ответ Создать тему
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2024, CyberForum.ru