Logs: freenode/#haskell
| 2020-10-26 15:32:14 | <thblt> | tomsmeding: isn't this a compile error? |
| 2020-10-26 15:32:34 | <tomsmeding> | not if they were actually the same symbol in the beginning |
| 2020-10-26 15:32:44 | <thblt> | Ha, haven't thought of that. |
| 2020-10-26 15:32:52 | <tomsmeding> | e.g. Foo exports foo, A and B re-export foo from Foo, and Main imports A and B and uses foo |
| 2020-10-26 15:33:14 | tomsmeding | now wonderse what ghc does if you make both the A and the B import of foo explicit |
| 2020-10-26 15:33:22 | <thblt> | And ghc is happy with that? As long as the symbol's definition isn't ambiguous? |
| 2020-10-26 15:33:27 | <tomsmeding> | yup |
| 2020-10-26 15:33:37 | → | texasmynsted joins (~texasmyns@99.96.221.112) |
| 2020-10-26 15:33:39 | <thblt> | Makes sense. |
| 2020-10-26 15:34:44 | <tomsmeding> | if Main has 'import A (foo)' 'import B (foo)', ghc is completely fine |
| 2020-10-26 15:34:57 | <tomsmeding> | I guess that's one way to make the output of our imaginary tool unambiguous? |
| 2020-10-26 15:35:41 | <thblt> | This tool pretends to do that https://github.com/serokell/importify |
| 2020-10-26 15:35:44 | <tomsmeding> | there is already a tool to prune unused imports (https://hackage.haskell.org/package/fix-imports), but it doesn't convert implicit imports (import A) to explicit ones (import A (foo)) |
| 2020-10-26 15:35:57 | <thblt> | but archived |
| 2020-10-26 15:36:13 | × | Ivan__1 quits (~yudin@193.137.102.254) (Ping timeout: 265 seconds) |
| 2020-10-26 15:36:49 | <tomsmeding> | > In the future, we plan for Importify to be able to: [...] Convert imports between implicit and explicit, [...] |
| 2020-10-26 15:36:50 | <lambdabot> | <hint>:1:14: error: <hint>:1:14: error: parse error on input ‘,’ |
| 2020-10-26 15:36:51 | <tomsmeding> | it doesn't ;) |
| 2020-10-26 15:36:57 | <thblt> | Ha yes, read too fast. |
| 2020-10-26 15:37:19 | → | __monty__ joins (~toonn@unaffiliated/toonn) |
| 2020-10-26 15:37:33 | → | fendor_ joins (~fendor@91.141.2.240.wireless.dyn.drei.com) |
| 2020-10-26 15:38:23 | <thblt> | OK, I have another stupid question. I wrote a simple number guessing game using monad transformers, and it should work I think, but… I have no idea how to *start* the game. Here's the code https://paste.thb.lt/1603726423.lhs.html |
| 2020-10-26 15:38:26 | × | bartemius quits (~bartemius@109-252-20-20.nat.spd-mgts.ru) (Remote host closed the connection) |
| 2020-10-26 15:38:34 | <thblt> | The question is: what's the type of the thing that takes a GConf, inits a GState and actually instantiates a Game? |
| 2020-10-26 15:39:19 | × | fendor quits (~fendor@078132040188.public.t-mobile.at) (Ping timeout: 246 seconds) |
| 2020-10-26 15:39:53 | <thblt> | Game is type Game = ReaderT GConf (StateT GState IO) |
| 2020-10-26 15:40:05 | × | elliott_ quits (~elliott_@pool-108-51-141-12.washdc.fios.verizon.net) (Read error: Connection reset by peer) |
| 2020-10-26 15:40:52 | <tomsmeding> | what about https://hackage.haskell.org/package/mtl-2.2.2/docs/Control-Monad-Reader.html#v:runReader and https://hackage.haskell.org/package/mtl-2.2.2/docs/Control-Monad-State-Lazy.html#v:runState ? |
| 2020-10-26 15:41:04 | <thblt> | tomsmeding: reading this! |
| 2020-10-26 15:41:13 | <tomsmeding> | oh runReaderT and runStateT of course, because transformers |
| 2020-10-26 15:41:14 | → | Tuplanolla joins (~Tuplanoll@91-159-68-239.elisa-laajakaista.fi) |
| 2020-10-26 15:42:08 | × | firstlove quits (~firstlove@58.246.122.242) (Ping timeout: 256 seconds) |
| 2020-10-26 15:43:16 | → | Ivan__1 joins (~yudin@gw.mat.uc.pt) |
| 2020-10-26 15:46:16 | → | elliott_ joins (~elliott_@pool-108-51-141-12.washdc.fios.verizon.net) |
| 2020-10-26 15:46:23 | × | alp quits (~alp@2a01:e0a:58b:4920:f036:1a06:bf83:85b) (Ping timeout: 272 seconds) |
| 2020-10-26 15:47:06 | → | Deide joins (~Deide@217.155.19.23) |
| 2020-10-26 15:48:47 | <thblt> | I feel stupid, but in ghci, `runReaderT play def` just prints `runReaderT play def :: StateT GState IO ()` |
| 2020-10-26 15:49:40 | <monsterchrom> | add runStateT on top of that |
| 2020-10-26 15:49:40 | <__monty__> | You'll probably want to runStateT on that? |
| 2020-10-26 15:50:04 | → | alp joins (~alp@2a01:e0a:58b:4920:c83a:4ff:4d6e:6312) |
| 2020-10-26 15:50:07 | <monsterchrom> | Yes this is what happens when you go crazy with monad transformers. |
| 2020-10-26 15:50:24 | <monsterchrom> | piled higher and deeper |
| 2020-10-26 15:50:25 | <[exa]> | thblt: runReaderT translates ReaderT r x a to `x a`, in your case this continues because x=StateT... |
| 2020-10-26 15:50:54 | <thblt> | monsterchrom: is that so crazy? a config ReaderT, a runtime state and IO? |
| 2020-10-26 15:51:10 | <thblt> | (Thanks all) |
| 2020-10-26 15:51:21 | × | geowiesnot quits (~user@i15-les02-ix2-87-89-181-157.sfr.lns.abo.bbox.fr) (Ping timeout: 256 seconds) |
| 2020-10-26 15:51:35 | <monsterchrom> | You look at "runStateT (runReaderT play def) initial", you tell me. |
| 2020-10-26 15:51:43 | × | heatsink quits (~heatsink@107-136-5-69.lightspeed.sntcca.sbcglobal.net) (Remote host closed the connection) |
| 2020-10-26 15:51:54 | <thblt> | monsterchrom: i honestly don't know. |
| 2020-10-26 15:51:59 | <monsterchrom> | for starters, the sheer obligation to say that in the correct order |
| 2020-10-26 15:52:34 | → | idhugo_ joins (~idhugo@563472ae.rev.stofanet.dk) |
| 2020-10-26 15:52:37 | <T0pH4t> | is there a way to put a type constraint on a type family decl eg "class Foo a where type Bar a" where i limit the type set for "Bar a" to be an instance of some class Baz |
| 2020-10-26 15:52:44 | × | elliott__ quits (~elliott@pool-108-51-141-12.washdc.fios.verizon.net) (Ping timeout: 258 seconds) |
| 2020-10-26 15:53:30 | → | unihernandez22 joins (~Unai@168.197.200.20) |
| 2020-10-26 15:54:20 | × | unihernandez22 quits (~Unai@168.197.200.20) (Client Quit) |
| 2020-10-26 15:55:10 | → | Guest23433 joins (~Waithamai@185.244.214.217) |
| 2020-10-26 15:55:48 | <thblt> | monsterchrom: I think I see what you mean. I thought it was a common pattern. |
| 2020-10-26 15:55:50 | <__monty__> | monsterchrom: Would you recommend MTL instead (or another effect system)? Or rather just define a monad per-project? |
| 2020-10-26 15:56:01 | <tomsmeding> | T0pH4t: I don't think so, but maybe you can make this work: "class Baz a => Foo a where type Bar a" |
| 2020-10-26 15:56:28 | <dolio> | thblt: I don't see a problem. |
| 2020-10-26 15:56:41 | <monsterchrom> | Define a monad per project. And, ironically, its definition is a newtype wrapper around using MTL stuff. |
| 2020-10-26 15:56:50 | × | alx741 quits (~alx741@186.178.110.169) (Ping timeout: 260 seconds) |
| 2020-10-26 15:57:00 | <monsterchrom> | err I guess transformers stuff. |
| 2020-10-26 15:57:09 | <T0pH4t> | ]tomsmeding: that woudl only constrain 'a' and not the type of "Bar a" |
| 2020-10-26 15:57:26 | <T0pH4t> | tomsmeding: ^ |
| 2020-10-26 15:57:26 | <tomsmeding> | monsterchrom: wanting the newtype does not mean that you can't have more than 1 monad stack per project |
| 2020-10-26 15:58:03 | <tomsmeding> | and you just move the problem: you still have to say runStateT (runReaderT blabla), but now just in runMyMonad instead of in main |
| 2020-10-26 15:58:09 | <monsterchrom> | So define two newtype wrappers of two stacks? |
| 2020-10-26 15:58:13 | <tomsmeding> | yes! |
| 2020-10-26 15:58:27 | <thblt> | GHC has been screaming at me a few times talking about "functional dependencies". What can I read to understand what it's screaming about? |
| 2020-10-26 15:58:35 | → | heatsink joins (~heatsink@107-136-5-69.lightspeed.sntcca.sbcglobal.net) |
| 2020-10-26 15:58:40 | <tomsmeding> | T0pH4t: ah that's true; then I don't think that's possible |
| 2020-10-26 15:58:44 | → | fendor__ joins (~fendor@078132040188.public.t-mobile.at) |
| 2020-10-26 15:58:45 | × | fendor_ quits (~fendor@91.141.2.240.wireless.dyn.drei.com) (Ping timeout: 240 seconds) |
| 2020-10-26 15:58:54 | <monsterchrom> | OK, inside the newtype wrapper it doesn't have to be transformers stuff. You can handcode it yourself. That's a choice. |
| 2020-10-26 15:59:38 | <texasmynsted> | The ~/.cabal/config has only seven options listed in the init section. How do people normally make a template for cabal init? I have done this with "template" programs, but it seems like there must be a better way. |
| 2020-10-26 15:59:43 | <[exa]> | thblt: functional dependencies arise to disambiguate various stuff with multiparameter type classes, I guess you just hit some minor problematic spot |
| 2020-10-26 15:59:56 | <monsterchrom> | I have done "newtype X a = MkX (String -> Maybe (String, a))" by hand. |
| 2020-10-26 16:00:24 | × | GyroW_ quits (~GyroW@unaffiliated/gyrow) (Quit: Someone ate my pie) |
| 2020-10-26 16:00:34 | → | GyroW joins (~GyroW@d54C03E98.access.telenet.be) |
| 2020-10-26 16:00:34 | × | GyroW quits (~GyroW@d54C03E98.access.telenet.be) (Changing host) |
| 2020-10-26 16:00:34 | → | GyroW joins (~GyroW@unaffiliated/gyrow) |
| 2020-10-26 16:00:34 | → | Rudd0 joins (~Rudd0@185.189.115.103) |
| 2020-10-26 16:01:05 | <monsterchrom> | If you're too lazy to write its >>=, you could choose "newtype X a = MkX (StateT String Maybe a)" and write a few "deriving" clauses. |
| 2020-10-26 16:01:36 | <tomsmeding> | I'm not sure whether coding something like that by hand would be easier than saying runStateT . runMaybeT for some definition of (.) |
| 2020-10-26 16:02:05 | <tomsmeding> | not saying it's particularly difficult, but I guess I don't really see your argument against transformer stacks anymore then :p |
| 2020-10-26 16:02:06 | <dolio> | Yeah, I don't get what's being optimized here. |
| 2020-10-26 16:03:12 | <monsterchrom> | Bah, that was a tangent. |
| 2020-10-26 16:03:13 | × | chkno quits (~chkno@75-7-2-127.lightspeed.sntcca.sbcglobal.net) (Read error: Connection reset by peer) |
| 2020-10-26 16:03:31 | <monsterchrom> | For this particular game, one doesn't need the StateT GState stage. |
| 2020-10-26 16:03:55 | → | chkno joins (~chkno@75-7-2-127.lightspeed.sntcca.sbcglobal.net) |
| 2020-10-26 16:04:02 | <tomsmeding> | ... or, apparently, I misunderstood you. Sorry for the confusion :p |
| 2020-10-26 16:04:04 | <thblt> | monsterchrom: of course! I wanted to learn about transformers, which was easier with a simple problem. |
| 2020-10-26 16:04:12 | <T0pH4t> | so this doesn't seem to work either :/ "class Baz a => Foo a where type Bar a, toBaz :: Baz (Bar a) => a -> Bar a" |
| 2020-10-26 16:04:31 | <monsterchrom> | And the ReaderT stage could be replaced by the equivalent but lighter (GConf ->) |
| 2020-10-26 16:04:58 | <tomsmeding> | T0pH4t: remove the 'Baz a =>' constraint on Foo? |
| 2020-10-26 16:05:11 | → | johnw joins (~johnw@haskell/developer/johnw) |
| 2020-10-26 16:05:15 | <tomsmeding> | oh oh oh maaaybe you can "class Baz (Bar a) => Foo a where type Bar a" |
| 2020-10-26 16:05:16 | <thblt> | monsterchrom: thanks for the tip! |
| 2020-10-26 16:05:16 | <T0pH4t> | woops, thats not there, wrong copy |
All times are in UTC.