Results 1 to 11 of 11

Thread: QTextStream cannot read £ characters?

  1. #1
    Join Date
    Jan 2006
    Location
    Scandinavia
    Posts
    62
    Thanks
    5
    Thanked 2 Times in 1 Post
    Qt products
    Qt3 Qt4
    Platforms
    Unix/X11 Windows

    Default QTextStream cannot read £ characters?

    By a mere chance I put in £ characters in a QString when I was unit testing write to/from text file.
    I noticed that using QTextStream to read back the data lost £ characters.

    Is it a locale thing? I've tried in on ubuntu only, not on Windows. Here's an example below where I show writing the text and then reading it back again. file.readAll() works like a charm but the other one doesn't

    Qt Code:
    1. #include <iostream>
    2. #include <QFile>
    3. #include <QTextStream>
    4. #include <QString>
    5. #include <QIODevice>
    6. namespace
    7. {
    8. const QString funky_text = " Yalla three:£[£££] \\£ three:#[###] \\# three:@[@@@] \\@ three:$[$$$] \\$ "; // with whitespace
    9.  
    10. void writeFile()
    11. {
    12. QFile file_out("/tmp/dummy.txt");
    13. const QIODevice::OpenMode write_mode = (QIODevice::WriteOnly | QIODevice::Truncate);
    14. if(!file_out.open(write_mode))
    15. {
    16. std::cerr << "Open (W) ERROR what's up:" << file_out.errorString().toStdString().c_str()<< std::endl << std::flush;
    17. return;
    18. }
    19. QTextStream stream(&file_out);
    20. stream << funky_text;
    21. file_out.close();
    22. }
    23.  
    24. void readVerify_1()
    25. {
    26. QFile file_in("/tmp/dummy.txt");
    27. const QIODevice::OpenMode read_mode = (QIODevice::ReadOnly | QIODevice::Text);
    28. if(!file_in.open(read_mode))
    29. {
    30. std::cerr << "Open (R) ERROR what's up:" << file_in.errorString().toStdString().c_str() << std::endl << std::flush;
    31. return;
    32. }
    33.  
    34. QString txt_in_1(file_in.readAll()); // conversion from QByteArray
    35. file_in.close();
    36. std::cout << "funky:" << funky_text.toStdString().c_str() << std::endl;
    37. std::cout << "QString(funky, txt1) = " << QString::compare(txt_in_1, funky_text, Qt::CaseSensitive) << std::endl;
    38. std::cout << "txt1: " << txt_in_1.toStdString().c_str() << std::endl;
    39. }
    40.  
    41. void readVerify_2()
    42. {
    43. // read it again but by using QTextStream
    44. QFile file_in("/tmp/dummy.txt");
    45. const QIODevice::OpenMode read_mode = (QIODevice::ReadOnly | QIODevice::Text);
    46. if(!file_in.open(read_mode))
    47. {
    48. std::cerr << "Open (R) ERROR what's up:" << file_in.errorString().toStdString().c_str() << std::endl << std::flush;
    49. return;
    50. }
    51. QTextStream stream(&file_in);
    52. QString txt_in_2 = stream.readAll();
    53. file_in.close();
    54.  
    55.  
    56. std::cout << "QString(funky, txt2) = " << QString::compare(txt_in_2, funky_text, Qt::CaseSensitive) << std::endl;
    57. std::cout << "txt2:" << txt_in_2.toStdString().c_str() << std::endl;
    58. }
    59.  
    60. void testQTextStream()
    61. {
    62. writeFile();
    63. readVerify_1();
    64. readVerify_2();
    65.  
    66. }
    67. } // namespace
    To copy to clipboard, switch view to plain text mode 

    This would give the following output
    funky: Yalla three:£[£££] \£ three:#[###] \# three:@[@@@] \@ three:$[$$$] \$
    QString(funky, txt1) = 0
    txt1: Yalla three:£[£££] \£ three:#[###] \# three:@[@@@] \@ three:$[$$$] \$
    QString(funky, txt2) = -103
    txt2: Yalla three:[] \ three:#[###] \# three:@[@@@] \@ three:$[$$$] \$
    txt2: Yalla three:[] \ three:#[###] \# three:@[@@@] \@ three:$[$$$] \$
    Obviously the £ signs are gone!


    Anyone with ideas?
    -- KjellKod

  2. #2
    Join Date
    Jan 2006
    Location
    Warsaw, Poland
    Posts
    33,359
    Thanks
    3
    Thanked 5,015 Times in 4,792 Posts
    Qt products
    Qt3 Qt4 Qt5 Qt/Embedded
    Platforms
    Unix/X11 Windows Android Maemo/MeeGo
    Wiki edits
    10

    Default Re: QTextStream cannot read £ characters?

    QString and QTextStream perform encoding coversion. If your source code is in UTF-8 and you're not using QString::fromUtf8() then you may have encoding issues. Try performing the conversion properly and see if it helps.
    Your biological and technological distinctiveness will be added to our own. Resistance is futile.

    Please ask Qt related questions on the forum and not using private messages or visitor messages.


  3. #3
    Join Date
    Nov 2010
    Posts
    315
    Thanked 53 Times in 51 Posts
    Qt products
    Qt4
    Platforms
    Unix/X11 Windows Symbian S60 Maemo/MeeGo

    Default Re: QTextStream cannot read £ characters?

    Just read: QTextStream::setCodec, QTextCodec and choose coding you are planing to use for this file (for example UTF-8).

  4. #4
    Join Date
    Jan 2006
    Location
    Scandinavia
    Posts
    62
    Thanks
    5
    Thanked 2 Times in 1 Post
    Qt products
    Qt3 Qt4
    Platforms
    Unix/X11 Windows

    Default Re: QTextStream cannot read £ characters?

    Thank you. Yes I'm aware of the QTextCodec and that you might have to set these. I was not aware that you HAD to set them every time!

    I mean if I don't set it when I write it down, but have to set it when I read it back then QTextStream seems very counter intuitive. Too me this is a bug, probably not a Qt programming-bug but a design-logic bug nonetheless.

    Thanks for the input though. My solution is just not to use QTextStream but QFile::readAll().

    Cheers

  5. #5
    Join Date
    Jan 2006
    Location
    Warsaw, Poland
    Posts
    33,359
    Thanks
    3
    Thanked 5,015 Times in 4,792 Posts
    Qt products
    Qt3 Qt4 Qt5 Qt/Embedded
    Platforms
    Unix/X11 Windows Android Maemo/MeeGo
    Wiki edits
    10

    Default Re: QTextStream cannot read £ characters?

    It's not a problem with the codec but rather with non-ascii characters in your source code.
    Your biological and technological distinctiveness will be added to our own. Resistance is futile.

    Please ask Qt related questions on the forum and not using private messages or visitor messages.


  6. The following user says thank you to wysota for this useful post:

    KjellKod (11th August 2011)

  7. #6
    Join Date
    Sep 2009
    Location
    UK
    Posts
    2,447
    Thanks
    6
    Thanked 348 Times in 333 Posts
    Qt products
    Qt4
    Platforms
    Windows

    Default Re: QTextStream cannot read £ characters?

    I'm suprised your code even compiles. Considering you are using non-ascii characters such as £, some complain.

  8. #7
    Join Date
    Jan 2006
    Location
    Scandinavia
    Posts
    62
    Thanks
    5
    Thanked 2 Times in 1 Post
    Qt products
    Qt3 Qt4
    Platforms
    Unix/X11 Windows

    Default Re: QTextStream cannot read £ characters?

    Quote Originally Posted by wysota View Post
    It's not a problem with the codec but rather with non-ascii characters in your source code.
    OK @wysota. I got it. I still think it's confusing that it works one way but not the other. To me it would make more sense if you had to put the codec in to both write it to file and then to read it back - not as it is now,. but I guess I just have to accept that is how QTextStream works

    Thanks.

  9. #8
    Join Date
    Sep 2009
    Location
    UK
    Posts
    2,447
    Thanks
    6
    Thanked 348 Times in 333 Posts
    Qt products
    Qt4
    Platforms
    Windows

    Default Re: QTextStream cannot read £ characters?

    KjellKod: No, that wasn't an attempt to flame, just pointing out that some compilers will simply throw an error on your test text as they only support ASCII (0x00 - 0x7F)

    Its my understanding that QTextStream has to "guess" the encoding format of the stream its reading, so the conversion is based on this guessed format - which may or may not be correct. If you fix the format there is no guessing. If you included the appropriate BOM (eg. 0xEF,0xBB,0xBF for UTF8) then there is also no need to guess (or state) the format.

  10. The following user says thank you to squidge for this useful post:

    KjellKod (12th August 2011)

  11. #9
    Join Date
    Jan 2006
    Location
    Warsaw, Poland
    Posts
    33,359
    Thanks
    3
    Thanked 5,015 Times in 4,792 Posts
    Qt products
    Qt3 Qt4 Qt5 Qt/Embedded
    Platforms
    Unix/X11 Windows Android Maemo/MeeGo
    Wiki edits
    10

    Default Re: QTextStream cannot read £ characters?

    Quote Originally Posted by KjellKod View Post
    OK @wysota. I got it. I still think it's confusing that it works one way but not the other. To me it would make more sense if you had to put the codec in to both write it to file and then to read it back - not as it is now,.
    It's exactly like you say it should be. The "problem" is converting both ways doesn't have to give you the initial value and the codec itself can't detect such situation. It is your responsibility to provide input that's compliant with what the codec you use expects. By the way, read about QT_NO_CAST_FROM_ASCII in QString docs.
    Your biological and technological distinctiveness will be added to our own. Resistance is futile.

    Please ask Qt related questions on the forum and not using private messages or visitor messages.


  12. #10
    Join Date
    Jan 2006
    Location
    Scandinavia
    Posts
    62
    Thanks
    5
    Thanked 2 Times in 1 Post
    Qt products
    Qt3 Qt4
    Platforms
    Unix/X11 Windows

    Default Re: QTextStream cannot read £ characters?

    Maybe time to enlighten me? Why using QTextStream instead of ofstream or ifstream?

    Let me clarify:
    Of course QTextStream has lots of nifty features but in the simple case of reading up a human-readable text,. potentially writing it down again as human-readable (and why not reading it yet again) it seems to be lacking.

    If you apply Codecs to QTextStream then if I understand it correctly strictly speaking non-ascii signs (but still very common) such as the brittish pound sign £ sign or the euro symbol will no longer be human-readable.

    If on the other hand you would use the std::fstream (ofstream, ifstream to be specific) then there's no such problem whatsoever.

    See the examle below:
    Qt Code:
    1. #include <string>
    2. #include <iostream>
    3. #include <fstream>
    4. #include <QString>
    5.  
    6. bool writeTextToFile(const QString &qfilename, const QString &msg, bool truncate_file)
    7. {
    8. std::string filename(qfilename.toStdString());
    9. std::ofstream out;
    10. std::ios_base::openmode mode = std::ios_base::out; // a little overkill since it's an Ofstream
    11. truncate_file ? mode |= std::ios_base::trunc : mode |= std::ios_base::app;
    12. out.open(filename.c_str(), mode);
    13. if (!out.is_open())
    14. {
    15. std::cerr << "Unable to open file for writing:[" << filename.c_str() << "], std::ios_base state: [" << out.rdstate() << "]" << std::endl << std::flush;
    16. return false;
    17. }
    18. out << msg.toStdString().c_str();
    19. return true;
    20. }
    21.  
    22.  
    23. QString readTextFromFile(const QString &qfilename)
    24. {
    25. std::string filename(qfilename.toStdString());
    26. std::ifstream in;
    27. in.open(filename.c_str(),std::ios_base::in);
    28. if(!in.is_open())
    29. {
    30. std::cerr << "WARNING: "Unable to open text file: %s << filename.c_str() << " std::ios_base state: " << in.rdstate() << std::endl << std::flush;
    31. return QString("");
    32. }
    33.  
    34. std::ostringstream oss;
    35. oss << in.rdbuf();
    36. std::string content(oss.str());
    37. return QString(content.c_str());
    38. }
    To copy to clipboard, switch view to plain text mode 

    Using the std::fstream libraries there's no issue. £ will be put into the file and still be human readable, and reading it back again and returning the text containing £ will also be OK.

  13. #11
    Join Date
    Jan 2006
    Location
    Warsaw, Poland
    Posts
    33,359
    Thanks
    3
    Thanked 5,015 Times in 4,792 Posts
    Qt products
    Qt3 Qt4 Qt5 Qt/Embedded
    Platforms
    Unix/X11 Windows Android Maemo/MeeGo
    Wiki edits
    10

    Default Re: QTextStream cannot read £ characters?

    Quote Originally Posted by KjellKod View Post
    Maybe time to enlighten me? Why using QTextStream instead of ofstream or ifstream?
    Short and to the point: Unicode.
    Your biological and technological distinctiveness will be added to our own. Resistance is futile.

    Please ask Qt related questions on the forum and not using private messages or visitor messages.


Similar Threads

  1. Replies: 2
    Last Post: 9th June 2010, 16:08
  2. read an xml file with Asian characters in QTextEdit
    By Boris Liao in forum Qt Programming
    Replies: 1
    Last Post: 23rd January 2010, 22:56
  3. Unicode/ASCII characters in QTextStream
    By yren in forum Qt Programming
    Replies: 3
    Last Post: 23rd November 2009, 18:25
  4. Replies: 5
    Last Post: 27th May 2009, 12:49
  5. Read/Write from QTextStream
    By tonde in forum Qt Programming
    Replies: 7
    Last Post: 31st July 2008, 16:51

Bookmarks

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  
Digia, Qt and their respective logos are trademarks of Digia Plc in Finland and/or other countries worldwide.