ASCII characters not printed in WCOUT and COUT - c++

I am trying to print some "special" characters (above 127) in the console, but somehow it doesn't get printed.
I have this small code snippet:
#include <iostream>
int main()
{
std::wcout << L"a■■■■■■■■■■■a■■■■■■■■■■■■■■a" << std::flush;
return 0;
}
it prints the 'a' but then... nothing. and it doesn't matter if I use cout/string or wcout/wstring. (with cout I only see "?" and in wcout nothing, it ends the stream)
The ascii code is 254 for this character. What can be happening here? I thought this is okay to print?

From the answer I linked to in the comments, I think this is your solution:
#include <fcntl.h>
#include <io.h>
_setmode(_fileno(stdout), _O_U8TEXT);

Related

fstream not working properly with russian text?

I work with russian a lot and I've been trying to get data from a file with an input stream. Here's the code, it's supposed to output only the words that contain no more than 5 characters.
#include <iostream>
#include <fstream>
#include <string>
#include <Windows.h>
using namespace std;
int main()
{
setlocale(LC_ALL, "ru_ru.utf8");
ifstream input{ "in_text.txt" };
if (!input) {
cerr << "Ошибка при открытии файла" << endl;
return 1;
}
cout << "Вывод содержимого файла: " << "\n\n";
string line{};
while (input >> line) {
if (line.size() <= 5)
cout << line << endl;
}
cout << endl;
input.close();
return 0;
}
Here's the problem:
I noticed the output didn't pick up all of the words that were actually containing less than 5 characters. So I did a simple test with the word "Test" in english and the translation "тест" in russian, the same number of characters. So my text file would look like this:
Test тест
I used to debugger to see how the program would run and it printed out the english word and left the russian. I can't understand why this is happening.
P.S. When I changed the code to if (line.size() <= 8) it printed out both of them. Very odd
I think I messed up my system locale somehow I don't know. I did one time try to use std::locale
without really understanding it, maybe that did something to my PC I'm not really sure. Please help
I'm very unsure about this but using codecvt_utf8 and wstring_convert seems to work:
#include <codecvt> // codecvt_utf8
#include <string>
#include <iostream>
#include <locale> // std::wstring_convert
int main() {
// ...
while (input >> line) {
// convert the utf8 encoded `line` to utf32 encoding:
std::wstring_convert<std::codecvt_utf8<char32_t>, char32_t> u8_to_u32;
std::u32string u32s = u8_to_u32.from_bytes(line);
if (u32s.size() <= 5) // check the utf32 length
std::cout << line << '\n'; // but print the utf8 encoded string
}
// ...
}
Demo

How to read in Hebrew letters in Visual Studios C++

I'm trying to read in a Hebrew text file, do some modifications, then send it to another text file. I've been successful in displaying Hebrew letters using UTF8, but I can't seem to read them in. This code successfully prints out the Hebrew letters to the txt file that it was redirected to, but when I try to read in Hebrew from another text file (that was redirected in) I get random garbage. How do I fix this?
#include <iostream>
#include <string>
#include <fcntl.h>
#include <io.h>
#include <fstream>
using namespace std;
int main() {
_setmode(_fileno(stdout), _O_U8TEXT);
wprintf(L"\x05D0");//works with courier new in terminal
wchar_t example[] = L"א";
wcout << endl << example << endl;
wstring x;
getline(wcin, x);
wcout << x;
return 0;
}
Output
א
א
×××× ×©××ת ×× × ×שר×× ××××× ×צר××× ×ת ××¢×§× ××ש ××××ª× ××× â¬
The problem has been figured out. It was what Barmak Shemirani said almost. I put in _setmode(_fileno(stdin), _O_U16TEXT); and changed my output to U16 and then still got garbage then I changed them both to U8 and I was able to read in and out perfectly.

C++ setlocale for any region

I've written a little program for testing purposes because when using cout, the German letters ü ö ä ß were not displayed as they should but rather rubbish was given out on the console. However, using these lines
#include <iostream>
#include <locale>
using namespace std;
int main()
{
setlocale(LC_ALL, "German");
cout << "üüü ööö äää ßßß" << '\n';
system("pause");
return 0;
}
have solved this problem, at least as far as the German letters go. When I tried the same for Russian, i. e.
#include <iostream>
#include <locale>
using namespace std;
int main()
{
setlocale(LC_ALL, "RUSSIAN");
cout << "Кирилица" << '\n';
system("pause");
return 0;
}
this doesn't work anymore. What is going wrong here? Am I missing something about the setlocale function? My goal is to adapt the respective program to the writing system that is used, for example Cyrillic like aboe or Chinese or whatever.
FOR GERMAN -> std::setlocale(LC_ALL, "de_DE");
FOR RUSSIAN -> std::setlocale(LC_ALL, "rus");

How do i read just a single whitespace only from stdin/cin in C++?

I'm having trouble translating the following piece of Java code into its C++ equivalent, meant to be a simple routine to parse an input stream:
String word = br.readLine();
Given a sample input file, with the contents displayed in hex by piping through od -bc, the following is obtained:
...
0000020 040 012 ...
\n
...
indicating that I've made the input file correctly, by supplying on this one line a space character, following a newline character.
Java is able to read in the entire string a '<space>\n', but the C++ functions like fgets(), sscanf(), getchar()..., and their equivalent family of functions, all fail to detect this space rather than ignoring it, so instead i'm returned a zero-length string.
What is the idiomatic way to do this?
My g++ compiler details:
Target: i686-apple-darwin11
Thread model: posix
gcc version 4.2.1 (Based on Apple Inc. build 5658) (LLVM build 2336.1.00)
Code + Sample input (mirrored # https://gist.github.com/1933400)
#include <tr1/unordered_map>
#include <stdio.h>
#include <cstdio>
#include <iostream>
#include <cassert>
#include <algorithm>
#include <string>
#include <cstdlib>
#include <cstring>
#include <queue>
#include <vector>
#include <string.h>
#include <ctime>
#include <stdlib.h>
#include <math.h>
#include <string>
#include <locale>
#include <sys/time.h>
#include <iterator>
using namespace std;
#define REP(i, a, b) for(int i=int(a); i<int(b); ++i)
const int MAX_WORD_LENGTH = 22;
char word[MAX_WORD_LENGTH];
string sz_word;
int N, M;
int main()
{
scanf("%d %d\n", &N, &M);
REP(i,0,N)
{
memset(word, 0, MAX_WORD_LENGTH);
scanf("%s\n", word);
//if (i == N-1)
// cout << word << endl;
}
REP(i,0,M)
{
std::getline(std::cin, sz_word);
cout << "word: '" << sz_word << "'" << endl;
}
return 0;
}
Sample input:
1 1
1
<space>
The C++ equivalent is (assuming br is some kind of std::istream):
std::string word;
std::getline(br, word);
If you're reading from standard input:
std::getline(std::cin, word);
The functions you list are all C functions; they're available in C++ if you really want them, but the C++ library is usually more convenient.
UPDATE: having seen your real code, the problem is that you're mixing C and C++ style input; this is usually a bad idea, and requires some care to get it right if you really have to. The problems are:
\n on the end of the scanf strings will match any amount of whitespace; it will keep matching any newlines until you enter something other than whitespace. Just remove the \n.
After the last scanf, there is still an unmatched \n in the input stream, so the first getline will give an empty line. You can call std::cin.ignore() to skip that newline.
The best solution would be to use std::cin for all input, and not try to use the <cstdio> functions at all. You can read numbers using the formatted extraction operator: std::cin >> N >> M;
If I may simplify your program and restate your question:
#include <cstdio>
#include <iostream>
#include <string>
char word[22];
std::string sz_word;
int main()
{
std::scanf("%s\n", word);
std::cout << "'" << word << "'" << std::endl;
std::getline(std::cin, sz_word);
std::cout << "word: '" << sz_word << "'" << std::endl;
return 0;
}
An appropriate input is this:
11
22
Note the space at the beginning of the 2nd line. The expected output is:
'11'
word: ' 22'
The observed output is:
'11'
word: '22'
Now then, why is the expected output different from the observed output?
Answer: Because you called scanf. From the Linux man page:
The format string consists of a sequence of directives ...A directive is one of the following ...
A sequence of white-space characters (space, tab, newline, etc.; see isspace(3)). This directive matches any amount of white space, including none, in the input.
So, the \n in your scanf format string matches any amount of white space, including the initial white space on the subsequent line.
fgets() really should work, it's not documented as "eating" white space, it even includes the line feed in the returned string.
Well something that could help solve your problem with the reading in whitespace.
char space[1];
// then set the character to either a NULL or to a basic ' ' <space>
SO. for example with your code instead of calling the scanf() I would instead make a constructor or just a setSpace() type function. Strings can be really messy so I would also get rid of those if at all possible.
Hope this maybe at least inspires some thought somewhere...

Unable to write a std::wstring into wofstream

I'm using Qt/C++ on a Linux system. I need to convert a QLineEdit's text to std::wstring and write it into a std::wofstream. It works correctly for ascii strings, but when I enter any other character (Arabic or Uzbek) there is nothing written in the file. (size of file is 0 bytes).
this is my code:
wofstream customersFile;
customersFile.open("./customers.txt");
std::wstring ws = lne_address_customer->text().toStdWString();
customersFile << ws << ws.length() << std::endl;
Output for John Smith entered in the line edit is John Smith10. but for unicode strings, nothing.
First I thought that is a problem with QString::toStdWString(), but customersFile << ws.length(); writes correct length of all strings. So I guess I'm doing something wrong wrong with writing wstring in file. [?]
EDIT:
I write it again in eclipse. and compiled it with g++4.5. result is same:
#include <iostream>
#include <string>
#include <fstream>
using namespace std;
int main()
{
cout << "" << endl; // prints
wstring ws = L"سلام"; // this is an Arabic "Hello"
wofstream wf("new.txt");
if (!wf.bad())
wf << ws;
else
cerr << "some problem";
return 0;
}
Add
#include <locale>
and at the start of main,
std::locale::global(std::locale(""));