Wczytywanie pliku txt - błąd z polskimi znakami

0

Witam. Od niedawna piszę w C++, do tej pory cały czas pisałem w Delphi. No i mam taki oto problem. Muszę do comboboxa wczytać zawartość pliku txt. Wszystko ładnie pięknie tylko że po wczytaniu zamiast polskich znaków mam przysłowiowe krzaczki. Szukałem już tutaj na forum i u wujka google ale nie mogłem nic znaleźć, nic dopasować do mojego kodu. Pracuje w Visual c++ 2010 Express.

Oto kod całej procedury:

		 		std::fstream plik;
				 String^ S = Application::StartupPath + "\\info.txt";
				 char* S1 = (char*)System::Runtime::InteropServices::Marshal:: StringToHGlobalAnsi(S).ToPointer();
				 plik.open(S1, std::ios::in);
				 if( plik.good() == true )
				 {
					 std::string p;
					 getline( plik,p );
					 while (p != "")
					 {
						ComboBox1->Items->Add(ToSysString(p));
						getline( plik,p );
					 }
					 plik.close();
				 } 

Dodatkowo daje kod funkcji konwertującej std::string na System::String^ użytej w powyższej procedurze

System::String^ ToSysString(std::string source)
	{
		System::String^ result;
		int len = (int)source.length();
		for(int i=0; i<len; i++)
			result += (wchar_t)source[i];
		return result;
	} 

Z góry dziękuje za pomoc

0

Dzięki bsrh. Teraz wszystko działa poprawnie.

Oto nowy kod:

					array<System::String ^> ^s = System::IO::File::ReadAllLines(Application::StartupPath + "\\info.txt",System::Text::Encoding::Default);
					int i = 0;
					while (s->Length - 1 > i) 
					{
						ComboBox1->Items->Add(s[i++]);
					} 
0
System::Text::Encoding::Default

To to raczej zbędne jest, jak odpalisz Read*** bez podania kodowania to Default zostanie i tak użyty :)

0

W ogóle to właśnie pomyślałem że można zrobić to z http://msdn.microsoft.com/en-us/library/system.windows.forms.combobox.objectcollection.addrange.aspx
Z tym to było by coś takiego:

ComboBox1->Items->AddRange(System::IO::File::ReadAllLines(Application::StartupPath + "\\info.txt")

Sweetaśne co nie? :)

0

Dodatkowo daje kod funkcji konwertującej std::string na System::String^ użytej w powyższej procedurze

pomijając już fakt, że lepiej było użyć .Netowych funkcji i wywalić to zupełnie, to ta funkcja jest przekombinowana, bo System::String ma konstruktor pobierający C-stringa, co można połączyć z metodą std::string.c_str()

  std::string string1 = "ala ma kota";
  System::String ^string2 = gcnew System::String(string1.c_str()); // tadaam!

w twoim kodzie jest też takie coś:

char* S1 = (char*)System::Runtime::InteropServices::Marshal:: StringToHGlobalAnsi(S).ToPointer();

co jest nienajlepszym rozwiązaniem, bo trzeba pamiętać o zwolnieniu S1 za pomocą FreeHGlobal.
zamiast tego można:

#include <iostream>
using namespace std;

int main()
{
  // przykładowy napis
  System::String ^napis = L"ala ma kota";

  // konwersja z Unicode do ANSI
  array<unsigned char>^ anapis = System::Text::Encoding::Default->GetBytes(napis);

  // wyjęcie tablicy spod Garbage Collectora (i pozbycie się „unsigned”)
  pin_ptr<char> pnapis = interior_ptr<char>(&anapis[0]);

  // zmiennej pnapis można używać jak char*
  cout << pnapis << endl;

  // pnapis wylatuje z zasięgu, i zostanie zwrócony garbage collectorowi
}

jeśli nie musimy pozbywać się „unsigned”, kod się trochę uprości bo nie trzeba rzutować przez interior_ptr:

#include <iostream>
using namespace std;
using namespace System::Text;

int main()
{
  System::String ^napis = L"ala ma kota";
  array<unsigned char>^ anapis = Encoding::Default->GetBytes(napis);
  pin_ptr<unsigned char> pnapis = &anapis[0];
  cout << pnapis << endl;
}

jeszcze wyjaśnię, że tablica anapis to kopia pierwotnego stringa, a pnapis jest wskaźnikiem na zawartość tej tablicy.

1 użytkowników online, w tym zalogowanych: 0, gości: 1