none
verwirrendes Sortieren von Umlauten RRS feed

  • Frage

  • Hi,

    historisch gewachsen werden in den Programmteilen eigentlich alle Varianten
    verwendet: strcmp/strcoll, CString::Compare/Collate, die Windows-Funktion CompareString, ...

    Im Zuge von Aufräummassnahmen gehe ich dazu über, die meisten Vergleiche auf
    CompareString(LOCALE_SYSTEM_DEFAULT, NORM_IGNORECASE, Buf1, -1, Buf2, -1)
    umzustellen.

    lt. Wikipedia gibt es nach DIN 5007-1 zwei Sortiervarianten:
    ä=a und ä=ae

    Welche Parameter brauche ich denn für CompareString um jeweils eine der beiden Varianten abzubilden?
    Oder ist es etwas, was der Anwender unter Windows einstellen kann/muss?

    Ausserdem ist mir so, als ob über die verschiedenen Windowsversionen hinweg sich
    das Sortierverhalten bzgl. der Umlaute etwas geändert hat?

    Tschüß, Holger.

    Mittwoch, 22. September 2010 13:00

Antworten

  • Hallo Holger!

    ä=a und ä=ae

    Mach beachte erst mal, dass dies nur im Deutschen gibt.
    Diese Sortierung heisst bei Windows "German Phone-Book sorting".

    Hier ist mal der Code:

    // See: All right, mistakes were made #2 (What the %#$* is wrong with 
    German Phonebook sorting?)
    // http://blogs.msdn.com/b/michkap/archive/2007/05/05/2430935.aspx
    #include <Windows.h>
    #include <tchar.h>
    #include <stdio.h>
    
    void PrintResult(int compreStringResult)
    {
        switch(compreStringResult)
        {
        case CSTR_GREATER_THAN:
            printf("greater");
            break;
        case CSTR_EQUAL:
            printf("equal");
            break;
        case CSTR_LESS_THAN:
            printf("less");
            break;
        }
        printf("\n");
    }
    int _tmain()
    {
        const LCID lcid1 =
    MAKELCID(MAKELANGID(LANG_GERMAN,SUBLANG_DEFAULT), SORT_DEFAULT);
        const LCID lcid2 =
    MAKELCID(MAKELANGID(LANG_GERMAN,SUBLANG_DEFAULT), SORT_GERMAN_PHONE_BOOK);
         TCHAR *szBuf1 = _T("HÜBNER");
        TCHAR *szBuf2 = _T("HUEBNER");
         printf("german-default: ");
        PrintResult(CompareString(lcid1, NORM_IGNORECASE, szBuf1, -1,
    szBuf2, -1));
         printf("german-phone-book: ");
        PrintResult(CompareString(lcid2, NORM_IGNORECASE, szBuf1, -1,
    szBuf2, -1));
    }

    Für mehr Infos siehe auch:
    http://blogs.msdn.com/b/michkap/archive/2007/05/05/2430935.aspx
     Und ob sich ein Sorting-Verhalten im Lauf von Windows-Versionen ändert ist leicht zu beantworten, wenn Du erkennst, dass sich die Unicode-Sorting auch ständig ändert...

    Siehe dazu auch nochmals den oberen Post...
    Ansonsten für Locales musst Du nur den Blog des MS Gurus dazu lesen:
    http://blogs.msdn.com/b/michkap/


    Jochen Kalmbach (MVP VC++)
    Mittwoch, 22. September 2010 14:38

Alle Antworten

  • Hallo Holger!

    ä=a und ä=ae

    Mach beachte erst mal, dass dies nur im Deutschen gibt.
    Diese Sortierung heisst bei Windows "German Phone-Book sorting".

    Hier ist mal der Code:

    // See: All right, mistakes were made #2 (What the %#$* is wrong with 
    German Phonebook sorting?)
    // http://blogs.msdn.com/b/michkap/archive/2007/05/05/2430935.aspx
    #include <Windows.h>
    #include <tchar.h>
    #include <stdio.h>
    
    void PrintResult(int compreStringResult)
    {
        switch(compreStringResult)
        {
        case CSTR_GREATER_THAN:
            printf("greater");
            break;
        case CSTR_EQUAL:
            printf("equal");
            break;
        case CSTR_LESS_THAN:
            printf("less");
            break;
        }
        printf("\n");
    }
    int _tmain()
    {
        const LCID lcid1 =
    MAKELCID(MAKELANGID(LANG_GERMAN,SUBLANG_DEFAULT), SORT_DEFAULT);
        const LCID lcid2 =
    MAKELCID(MAKELANGID(LANG_GERMAN,SUBLANG_DEFAULT), SORT_GERMAN_PHONE_BOOK);
         TCHAR *szBuf1 = _T("HÜBNER");
        TCHAR *szBuf2 = _T("HUEBNER");
         printf("german-default: ");
        PrintResult(CompareString(lcid1, NORM_IGNORECASE, szBuf1, -1,
    szBuf2, -1));
         printf("german-phone-book: ");
        PrintResult(CompareString(lcid2, NORM_IGNORECASE, szBuf1, -1,
    szBuf2, -1));
    }

    Für mehr Infos siehe auch:
    http://blogs.msdn.com/b/michkap/archive/2007/05/05/2430935.aspx
     Und ob sich ein Sorting-Verhalten im Lauf von Windows-Versionen ändert ist leicht zu beantworten, wenn Du erkennst, dass sich die Unicode-Sorting auch ständig ändert...

    Siehe dazu auch nochmals den oberen Post...
    Ansonsten für Locales musst Du nur den Blog des MS Gurus dazu lesen:
    http://blogs.msdn.com/b/michkap/


    Jochen Kalmbach (MVP VC++)
    Mittwoch, 22. September 2010 14:38
  • Ach so... das Ergebnis des Testprogrammes ist natürlich:

    german-default: less
    german-phone-book: equal

    zumindest bei mir auf meinem Windows 7 x64.


    Jochen Kalmbach (MVP VC++)
    Mittwoch, 22. September 2010 14:44
  • Hi,

    "Jochen Kalmbach [MVP]" schrieb im Newsbeitrag news:21651af9-6129-44a1-84bd-9f58be1f9f4f@communitybridge.codeplex.com...

    Hallo Holger!

    ä=a und ä=ae

    Mach beachte erst mal, dass dies nur im Deutschen gibt.
    Diese Sortierung heisst bei Windows "German Phone-Book sorting".
    Hier ist mal der Code:

    // See: All right, mistakes were made #2 (What the %#$* is wrong with
    German Phonebook sorting?)
    // http://blogs.msdn.com/b/michkap/archive/2007/05/05/2430935.aspx
    #include <Windows.h>
    #include <tchar.h>
    #include <stdio.h>
    
    void PrintResult(int compreStringResult)
    {
       switch(compreStringResult)
       {
       case CSTR_GREATER_THAN:
           printf("greater");
           break;
       case CSTR_EQUAL:
           printf("equal");
           break;
       case CSTR_LESS_THAN:
           printf("less");
           break;
       }
       printf("\n");
    }
    int _tmain()
    {
       const LCID lcid1 =
    MAKELCID(MAKELANGID(LANG_GERMAN,SUBLANG_DEFAULT), SORT_DEFAULT);
       const LCID lcid2 =
    MAKELCID(MAKELANGID(LANG_GERMAN,SUBLANG_DEFAULT), SORT_GERMAN_PHONE_BOOK);
        TCHAR *szBuf1 = _T("HÜBNER");
       TCHAR *szBuf2 = _T("HUEBNER");
        printf("german-default: ");
       PrintResult(CompareString(lcid1, NORM_IGNORECASE, szBuf1, -1,
    szBuf2, -1));
        printf("german-phone-book: ");
       PrintResult(CompareString(lcid2, NORM_IGNORECASE, szBuf1, -1,
    szBuf2, -1));
    }

    Für mehr Infos siehe auch:
    http://blogs.msdn.com/b/michkap/archive/2007/05/05/2430935.aspx
    Und ob sich ein Sorting-Verhalten im Lauf von Windows-Versionen ändert ist leicht zu beantworten, wenn Du erkennst, dass sich die Unicode-Sorting auch ständig ändert...

    Siehe dazu auch nochmals den oberen Post...
    Ansonsten für Locales musst Du nur den Blog des MS Gurus dazu lesen:
    http://blogs.msdn.com/b/michkap/


    Jochen Kalmbach (MVP VC++)

    ah ja,
    ich glaube ich mache dann doch lieber Augen und Ohren zu vor dem Problem.
    Immerhin sortiert (zumindest Vista) der Explorer Dateinamen nach "Telefonbuch", unabhängig der
    Locale-Einstellung, Excel scheint immer nach "neuer" DIN-Variante zu sortieren,...
    Wieso sollte dann der Kunde bei unserem Programm eine spezifische Sortierung erwarten???

    Tschüß, Holger.

    Donnerstag, 23. September 2010 08:07