开发者

Haskell, Char, Unicode, and Turkish

For the Char data-type, how do I specify tha开发者_如何学JAVAt I want to use the Turkish i instead of the English i for the toLower and toUpper functions?


text and the text-icu package

As of 2011, your best bet is to use the text package, and the toLower function of the Text ICU package, which supports Char operations parameterized by a locale,

From this example:

import Data.Text (pack, unpack)
import Data.Text.ICU (LocaleName(Locale), toLower)

main = do
  let trLocale = Locale "tr-TR"
      upStr    = "ÇIİĞÖŞÜ"
      lowStr   = unpack $ toLower trLocale $ pack upStr
  putStrLn $ "toLower " ++ upStr ++ " gives " ++ lowStr

Running this:

> toLower ÇIİĞÖŞÜ gives çıiğöşü

while this example converts between String, you can also just leave the data in text format.


The Data.Char library in Haskell is not locale dependent. It works for all Unicode characters, but perhaps not in the way you would expect. In the corresponding Unicode chart you can see the mappings for "dotted"/"dotless" i's.

  • toUpper 'i' => 'I'
  • toUpper 'ı' => 'I'
  • toLower 'I' => 'i'
  • toLower 'İ' => 'i'

Thus, it is clear that neither of the two transforms are reversible. If you want reversible handling of Turkish characters, it seems you have to use either a C-library or roll your own.

UPDATE: The Haskell 98 report makes this quite clear, whereas the Haskell 2010 report only says that Char corresponds to a Unicode character, and does not as clearly define the semantics of toLower and toUpper.


A Simple Matter Of Programming:

import qualified Data.Char as Char

toLower 'I' = 'ı'
toLower x   = Char.toLower x

Then

toLower <$> "I AM LOWERCASE" == "ı am lowercase"  
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜