Using Overloaded Strings
Asked Answered
L

1

17

OverloadedStrings extension is really very useful, however it has some downsides. Consider the following function definition:

someFunction :: ToJSSTring a => a -> IO ()
someFunction = js_function . toJSSTring

In this case when if I want to pass a literal value I have to add a type signature explicitly when OverloadedStrings is enabled:

someFunction ("This is plain string" :: String)
someFunction ("And this one is Text" :: Data.Text.Text)

The reason for this necessity is quite obvious, I suppose OverloadedStrings was designed to ease the passing of literal values to functions that have strict type signatures, making the developer free from writing packs everywhere where a Text value is needed.

The question is there any way, say, to default all string literals without type signatures to Text, or String? Or should I just split my code to general functions (with the ToJSString type constraint) and arbitrary ones, which have strict type signatures for their arguments?

Longo answered 6/11, 2014 at 11:31 Comment(0)
M
33

You can turn on ExtendedDefaultRules as well (https://www.fpcomplete.com/user/snoyberg/random-code-snippets/overloadedstrings-defaults):

{-# LANGUAGE FlexibleInstances #-}
{-# LANGUAGE OverloadedStrings #-}
{-# LANGUAGE ExtendedDefaultRules #-}
import Data.Text (Text, pack)

newtype JSString = JSString Text
    deriving Show

class ToJSString a where
    toJSString :: a -> JSString
instance ToJSString [Char] where
    toJSString = toJSString . pack
instance ToJSString Text where
    toJSString = JSString

someFunction :: ToJSString a => a -> IO ()
someFunction = print . toJSString

main :: IO ()
main = someFunction "Hello World"

EDIT You may also want to add default (Text) to the top of your module to have it use Text instead of String by default.

Mckamey answered 6/11, 2014 at 12:30 Comment(2)
You never ceases to amaze me! Thanks a lot.Longo
FYI link is brokenPay

© 2022 - 2024 — McMap. All rights reserved.