Forum: D Programlama Dili RSS
Konsol Türkçe Karakter Hatası
Sayfa:  1  2  3  sonraki 
Avatar
zekeriyadurmus #1
Kullanıcı başlığı: Talha Zekeriya Durmuş
Üye Eki 2012 tarihinden beri · 701 mesaj · Konum: Samsun/Türkiye
Grup üyelikleri: Üyeler
Profili göster · Bu konuya bağlantı
Konu adı: Konsol Türkçe Karakter Hatası
string buf;
while (std.stdio.stdin.readln(buf)){
    writeln(buf);
}

şeklinde kodu yazıp çalıştırıyorum türkçe "ğüş" gibi bir ifade yazınca

"Unhandled exception at 0x76B34B32 (KernelBase.dll) in source.exe: 0xE0440001 (parameters: 0x02031700)."

hatasını veriyor :)

Ali hocam, Salih hocam yardımlarınızı bekliyorum.

Zekeriya
Bilgi meraktan gelir...
acehreli (Moderatör) #2
Kullanıcı başlığı: Ali Çehreli
Üye Haz 2009 tarihinden beri · 4527 mesaj
Grup üyelikleri: Genel Moderatörler, Üyeler
Profili göster · Bu konuya bağlantı
D programının UTF-8 kodları yazdırdığını biliyoruz. Alan taraf UTF-8 anlıyor mu? Bir başka deyişle: Konsol UTF-8'e ayarlı mı?

O kullanımda bir gariplik görüyorum. readln'ın buf diye parametre alanı o buf'ın üzerine yazar. Dolayısıyla immutable char'lardan oluşan string'in kullanılamıyor olmasını beklerdim. Gerçekten de benim denediğim dmd'de derleme hatası oluyor. string yerine char dilimi dener misin...

Ali
Avatar
zekeriyadurmus #3
Kullanıcı başlığı: Talha Zekeriya Durmuş
Üye Eki 2012 tarihinden beri · 701 mesaj · Konum: Samsun/Türkiye
Grup üyelikleri: Üyeler
Profili göster · Bu konuya bağlantı
D programının UTF-8 kodları yazdırdığını biliyoruz. Alan taraf UTF-8 anlıyor mu? Bir başka deyişle: Konsol UTF-8'e ayarlı mı?
Konsol kesinlikle utf8 değil :) ama ne olduğunu bilmiyorum :) utf8 e nasıl çevirebiliriz ki?

O kullanımda bir gariplik görüyorum. readln'ın buf diye parametre alanı o buf'ın üzerine yazar. Dolayısıyla immutable char'lardan oluşan string'in kullanılamıyor olmasını beklerdim. Gerçekten de benim denediğim dmd'de derleme hatası oluyor. string yerine char dilimi dener misin... 
Yeni bir d sürümü çıkmış onun üzerinde çalışıyor eski sürümde bende de olmuyordu.
Bilgi meraktan gelir...
acehreli (Moderatör) #4
Kullanıcı başlığı: Ali Çehreli
Üye Haz 2009 tarihinden beri · 4527 mesaj
Grup üyelikleri: Genel Moderatörler, Üyeler
Profili göster · Bu konuya bağlantı
Windows konsoluysa chcp 65001.

string konusunda yine de bir gariplik var. readln'ın immutable(char) üzerine yazamıyor olması gerek. Ben 'DMD64 D Compiler v2.064-devel-52cc287' ile deniyorum:
import std.stdio;
 
void main()
{
    string buf;
    while (std.stdio.stdin.readln(buf)){
        writeln(buf);
    }
}

Error: template std.stdio.File.readln does not match any function template declaration. Candidates are:
./phobos/std/stdio.d(842):        std.stdio.File.readln(S = string)(dchar terminator = '\x0a') if (isSomeString!S)
./phobos/std/stdio.d(932):        std.stdio.File.readln(C)(ref C[] buf, dchar terminator = '\x0a') if (isSomeChar!C && is(Unqual!C == C) && !is(C == enum))
./phobos/std/stdio.d(955):        std.stdio.File.readln(C, R)(ref C[] buf, R terminator) if (isSomeChar!C && is(Unqual!C == C) && !is(C == enum) && isBidirectionalRange!R && is(typeof(terminator.front == (dchar).init)))
Error: template std.stdio.File.readln(S = string)(dchar terminator = '\x0a') if (isSomeString!S) cannot deduce template function from argument types !()(immutable(dchar)[])
make: *** [deneme] Error 1


Ali
agora #5
Üye Tem 2013 tarihinden beri · 221 mesaj
Grup üyelikleri: Üyeler
Profili göster · Bu konuya bağlantı
Windows konsolda soyle bi ciktisi var

core.exception.UnicodeException@src\rt\util\utf.d(290): invalid UTF-8 sequence
----------------
0x00415690 in onUnicodeError
0x00402100 in _Dmain at C:\Users\admin\Desktop\NeOss\NeOss\main.d(35)
0x00410760 in extern (C) int rt.dmain2._d_run_main(int, char**, extern (C) int f
unction(char[][])*).void runMain()
0x0041079B in extern (C) int rt.dmain2._d_run_main(int, char**, extern (C) int f
unction(char[][])*).void runAll()
0x00410399 in _d_run_main
0x0040C43C in main
0x77AA8543 in BaseThreadInitThunk
0x77E6AC69 in RtlInitializeExceptionChain
0x77E6AC3C in RtlInitializeExceptionChain
acehreli (Moderatör) #6
Kullanıcı başlığı: Ali Çehreli
Üye Haz 2009 tarihinden beri · 4527 mesaj
Grup üyelikleri: Genel Moderatörler, Üyeler
Profili göster · Bu konuya bağlantı
Zekeriya, programın gerçekten UTF-8 okuduğundan emin misin? writeln yerine baytları teker teker yazdırır mısın. Her Türkçe harfe karşılık 2 bayt görmen gerek.

Ali
Avatar
zekeriyadurmus #7
Kullanıcı başlığı: Talha Zekeriya Durmuş
Üye Eki 2012 tarihinden beri · 701 mesaj · Konum: Samsun/Türkiye
Grup üyelikleri: Üyeler
Profili göster · Bu konuya bağlantı
buf ı char[] olarak değiştirdim. string[] olunca derleme hatası vermiyor ama writeln(cast(ubyte[]) buf); dediğim zaman da harfleri okuyamıyorum. char[] olunca okuyabiliyorum.

Rhodeus Script (0.0.3p, 21 August 2013)
>>>üü
[129, 129, 10]

Rhodeus Script (0.0.3p, 21 August 2013)
>>>ğ
[103, 10]
lodvar g

Error: Variable 'g' is not defined.
>>>ğüş
[103, 129, 115, 10]
lodvar güs

Error: Variable 'güs' is not defined.
>>>öçş
[148, 135, 115, 10]

Windows konsoluysa chcp 65001.
Programı direk çalıştırdığım için böyle bir komut giremiyorum :/

Zekeriya
Bilgi meraktan gelir...
acehreli (Moderatör) #8
Kullanıcı başlığı: Ali Çehreli
Üye Haz 2009 tarihinden beri · 4527 mesaj
Grup üyelikleri: Genel Moderatörler, Üyeler
Profili göster · Bu konuya bağlantı
zekeriyadurmus:
>>>üü
[129, 129, 10]

Evet, onlar UTF-8 kodları değil. ü için 129 tek değerini görüyorsak UTF-8 değil, kod tablosu kullanılıyor demektir.

Programı direk çalıştırdığım için böyle bir komut giremiyorum :/

Program içinden ayarlamak için SetConsoleCP ve SetConsoleOutputCP varmış:

  http://msdn.microsoft.com/en-us/library/ms682064.aspx

Google'layınca örnekleri bulunuyor.

Ali
Avatar
zekeriyadurmus #9
Kullanıcı başlığı: Talha Zekeriya Durmuş
Üye Eki 2012 tarihinden beri · 701 mesaj · Konum: Samsun/Türkiye
Grup üyelikleri: Üyeler
Profili göster · Bu konuya bağlantı
version(Windows)
{
    import std.c.windows.windows : SetConsoleCP, SetConsoleOutputCP;
    static this()
    {
        SetConsoleCP(65001);
        SetConsoleOutputCP(65001);
    }
}

Bu kodu buldum :) Şu an kodlarda bir hata var test edemiyorum test edince yazarım buraya sonuçları :)

Zekeriya
Bilgi meraktan gelir...
emre413 (Moderatör) #10
Kullanıcı başlığı: Celal Emre ÇİÇEK
Üye Tem 2009 tarihinden beri · 62 mesaj · Konum: Kırıkkale
Grup üyelikleri: Genel Moderatörler, Üyeler
Profili göster · Bu konuya bağlantı
Tekrardan merhabalar!

Son zamanlarda c ve c++ ile uğraşırken ben de aynı sorunları yaşamıştım. Komut satırı yazı tipini Lucida Console yapıp kod olarak da c++ için;

#include <windows.h>
#include <iostream>
 
using namespace std;
 
int main()
{
    SetConsoleCP(1254);
    SetConsoleOutputCP(1254);
 
    cout << "Türkçe Karakterler: ı I İ i ö Ö ü Ü ğ Ğ ç Ç ş Ş" << endl;
    return 0;
}

yazınca benim konsolda hatasız tüm karakterleri bastı. 1254 yerine 65001 kullanınca karakterleri yine hatalı basıyor. 65001 galiba başka bir alanda Türkçe'nin kodu.
agora #11
Üye Tem 2013 tarihinden beri · 221 mesaj
Grup üyelikleri: Üyeler
Profili göster · Bu konuya bağlantı
CodePage degeri yani

SetConsoleCP();

CTP_UTF8 olarak da ayarlanabiliyor.

SetConsoleCP(CP_UTF8);
SetConsoleOutputCP(CP_UTF8);

Bu calisir mi acaba?

C++'da bunun icin

WideCharToMultiByte ve MultiByteToWideChar ozellikleri vardi galiba. Windows icin boyleydi de D dilinde de kullanilabilirligi var mi bilmiyorum.
emre413 (Moderatör) #12
Kullanıcı başlığı: Celal Emre ÇİÇEK
Üye Tem 2009 tarihinden beri · 62 mesaj · Konum: Kırıkkale
Grup üyelikleri: Genel Moderatörler, Üyeler
Profili göster · Bu konuya bağlantı
Enteresan bir şekilde D için kodları denediğimde kod olarak 65001 kabul gördü, 1254 değil. D için şöyle bir kod yazdım:

import std.stdio;
import core.sys.windows.windows;
 
extern(Windows) {
    bool SetConsoleCP(uint wCodePageID);
    bool SetConsoleOutputCP(uint wCodePageID);
}
 
void main() {
    SetConsoleCP(65001);
    SetConsoleOutputCP(65001);
 
    stdout.writeln("Türkçe Karakterler: ı I İ i ö Ö ü Ü ğ Ğ ç Ç ş Ş");
}

bu kod çalıştı. 65001 yerine 1254 yazınca karakterler bozuk çıktı. Aynı API fonksiyonu ancak farklı değer istiyor, garip! :)

Ekleme:

Ya şöyle bir durum var. Code::Blocks kullanıyorum. c++ için döküman encodingini UTF-8 yapınca bu sefer de D'de olduğu gibi 65001 çalıştı, 1254 bozuk karakter çıkardı.

Özet:

Döküman encodingi UTF-8 ise 65001 çalışıyor, WINDOWS-1254 ise 1254 çalışıyor. Forumdakiler genelde UTF-8 ile çalışıyor galiba? O yüzden kod olarak bu mesajdaki kodu kullansak problem çıkmaz herhalde.
Bu mesaj emre413 tarafından değiştirildi; zaman: 2013-08-22, 14:46.
acehreli (Moderatör) #13
Kullanıcı başlığı: Ali Çehreli
Üye Haz 2009 tarihinden beri · 4527 mesaj
Grup üyelikleri: Genel Moderatörler, Üyeler
Profili göster · Bu konuya bağlantı
emre413:
Enteresan bir şekilde D için kodları denediğimde kod olarak 65001 kabul gördü, 1254 değil.

D programı UTF-8 işlediğine göre 65001 olması gerekir çünkü Unicode'un 1254 numaralı kod tablosundaki karakter kodlarıyla ilgisi yok.

65001 yerine 1254 yazınca karakterler bozuk çıktı.

D çalışma ortamı karakterleri girişten teker teker alıyor ve onları UTF-8 kodları olarak kabul ediyor. Dolayısıyla konsolun ü'yü temsil etmek için UTF-8'deki karşılığı olarak girişe 2 bayt yerleştirmesi şart. Bunu değiştirmek olanaksız.

Aynı şey çıkış için de gerekli. D programı ü'yü çıkışa 2 bayt olarak yazdırıyor. Doğru işlemesi için konsolun da UTF-8'e ayarlı olması şart. Yoksa o iki baytın 1254'te karşılık geldikleri iki karakter olarak yazdırır.

Ali
acehreli (Moderatör) #14
Kullanıcı başlığı: Ali Çehreli
Üye Haz 2009 tarihinden beri · 4527 mesaj
Grup üyelikleri: Genel Moderatörler, Üyeler
Profili göster · Bu konuya bağlantı
Yanıtlanan mesaj #12
emre413:
c++ için döküman encodingini UTF-8 yapınca bu sefer de D'de olduğu gibi 65001 çalıştı

Öyle yapınca kaynak kod içindeki dizgi hazır değeri içindeki ü karakteri de dizgide iki bayt yer tutmaya başladı. (strlen ile bakabilirsin.) Dolayısıyla, ü karakteri iki bayt ile temsil ediliyorsa konsolun da o iki bayta karşılık ü'yü gösterecek biçimde ayarlanması şart.

Ali
agora #15
Üye Tem 2013 tarihinden beri · 221 mesaj
Grup üyelikleri: Üyeler
Profili göster · Bu konuya bağlantı
Yanıtlanan mesaj #12
emre413:
Enteresan bir şekilde D için kodları denediğimde kod olarak 65001 kabul gördü, 1254 değil. D için şöyle bir kod yazdım:

import std.stdio;
import core.sys.windows.windows;
 
extern(Windows) {
    bool SetConsoleCP(uint wCodePageID);
    bool SetConsoleOutputCP(uint wCodePageID);
}
 
void main() {
    SetConsoleCP(65001);
    SetConsoleOutputCP(65001);
 
    stdout.writeln("Türkçe Karakterler: ı I İ i ö Ö ü Ü ğ Ğ ç Ç ş Ş");
}

bu kod çalıştı. 65001 yerine 1254 yazınca karakterler bozuk çıktı. Aynı API fonksiyonu ancak farklı değer istiyor, garip! :)

Bende hala calismadi 65001 ya da 1254 :(
Doğrulama Kodu: VeriCode Lütfen resimde gördüğünüz doğrulama kodunu girin:
İfadeler: :-) ;-) :-D :-p :blush: :cool: :rolleyes: :huh: :-/ <_< :-( :'( :#: :scared: 8-( :nuts: :-O
Özel Karakterler:
Sayfa:  1  2  3  sonraki 
Bağlı değilsiniz. · Şifremi unuttum · ÜYELİK
This board is powered by the Unclassified NewsBoard software, 20100516-dev, © 2003-10 by Yves Goergen
Şu an: 2017-11-19, 05:59:43 (UTC -08:00)