haskell-jp / questions #42

ざっと見、ネストが深くなった最初の行の空白を二重にパースしようとしている感じがします(whenJust mNumofSpaces のところで一回、その行自体を含めて続きを many1 $ do でパースしつづけるので、その行は blockParser (Just $ numOfSpaces + s) でもう一回)。
現状だとこれが返ってくるんです。
Right 
    [ List 
        [ ListItem "list1"
        , ListItem " item1"
        , ListItem " item2"
        , ListItem " item3"
        , ListItem "list2"
        , ListItem "list3"
        ] 
    ]
最初は Nothing から Just 1 のインデントになるところはたぶん問題なく動いちゃうと思うんですが、 Just 1 のインデントのつもりで " item1" の行をパースすると、まず1個スペースを読み飛ばして、残り1個のスペースの個数を数えて、合計2になって、その Just 2 を持って " item1\n item2\n item3\n..." をパースする(最初の item1 の行にすでに残り一個しか空白がないことに注意)のでうまくいかないんじゃないかと
bulletpointParser として try しそこねたので itemParser でパースしちゃって ListItem " item1" が返る。そして次の行でまた Just 1 の bulletpointParser で同じことが起きる…の繰り返しになりそうです
なんとなく原因はわかったけど、ではどうすればいいのかっていうところが疲れててわからない。
現状の延長で手っ取り早くやるなら一行目だけ特別扱いするのがいいんじゃないでしょうかねえ…空白を数えてしまった後はかならず itemParser できるはずなのでそこだけ自前でやって、残りを many1 じゃなくて many で処理してくっつける、みたいな感じで
先頭の空白を \s[^\s] でパースすると
bar (空白1つ) にマッチして foo (空白2つ)にマッチしないようになるので、まずはこれをitemParserみたいに名付けて、あとはそれ以前の空白の数でネストを数えると、字句解析がうまくいきそう :face_with_rolling_eyes:
(貼っていただいたソース見てなくてすみません)
(本文中の正規表現は適宜パーサーコンビネータの表現に置き換えて読んでください:eyeglasses:)
foo (空白1つ)は itemParser で、
faa (空白2つ)は \s >> itemParser で、
waa (空白3つ)は \s >> \s >> itemParser
……パースできるイメージ。
ありがとー。よく見ておきます。
@aiya000
ごめんなさい。正規表現は全くわからないです(だからParsecに逃げました
ああ、やっぱり Maybe Int の Nothing をやめて単に Int の 0 にしたくなりますよね^^;
indentの数
@ さんの修正案を元に実装してみたら上手くいきました。ありがとうございます。
@heyclor has joined the channel
どのパッケージがどれだけの数のパッケージから依存されているか、をリスト化しているサイトがあったと思うのですが、わかる方いますでしょうか?
おお、まさにそれです!ありがとうございます!
stackage でもみれたきがする
見たいのは、依存されている数でした。
論文でいうと、どれだけ引用されているか、みたいな指標に近い感覚です。
stackage のリンクは依存されてるパッケージのリストです(もちろん 依存してるパッケージも別のページでみれますが)
Windowsでsupermonadパッケージを含むプロジェクトをビルドしようとすると、こんなエラーになります。解決方法が分かる方いたら教えて頂きたいです。他のパッケージはビルド出来ているので、supermonadがGHCプラグインを含んでいるせいで駄目なのかな?と予想しています
stackとcabal new-buildで試して同じエラーになりました。添付テキストはnew-buildの方です
あ、READMEに-dynamic付けてね、って書いてありましたね。stackやnew-buildではどう設定すればいいんでしょうか
--ghc-options=-dynamic
かな。
そういえばcabalファイルに書くのではダメでしたかね
そうですね。このページをみれば servant が、どれだけの数のパッケージから依存されているかはわかります。
知りたかったのは、 servant だけでなく、パッケージ a, b, c,... と候補が複数あったとき、どれがどれだけ非依存数をもっているか、のリストです。
--ghc-options=dynamic にすると、他のパッケージでも同じエラーが出るように……baseをこのオプション付きでビルドした奴が必要、という状況のようです
new-buildだと.projectファイルのオプションshared, executable-dynamicが関係ありそうだったんですが、有効にしても直らない模様
stackが落としてきたghcに無理やりパス通して使っているのも関係してるかもしれません
https://github.com/Hexirp/doctest-driver-gen/commit/610b470eaa22c6971693b08ebfe7f16bc6588fea のような変更をしたんですが https://travis-ci.org/Hexirp/doctest-driver-gen/builds/488028462#L479-L481 のように警告が出てしまいます。どういうことなんでしょうか? Cabal のドキュメントの条件節のところ () を見てもよくわかりません。
if ってのがグローバルなスコープでは駄目だよって言ってますね。スコープって言っていいのか分りませんけど。。。 誤解されるような言い方をすれば、インデントしてないところじゃ使えんよ。 って事なんでしょ。(厳密には libraryか、executableの中だけ)
Conditional blocks may appear anywhere inside a library or executable section

ということなんでそうなんでしょうね。。。
GHC 8.2以降の時だけtest-suiteを走らせたい場合、恐らく、
if impl(ghc < 8.2.0)
  buildable: False

と書くのが良いのではないかと。
Haskell-Yampaプログラムについてここにいる皆様のおかげでかなり形になりました!質問に対応してくださり本当にありがとうございます!
教授にクイックチェックの動作を見てもらってもらった感想として「テストを行うという目的としてテスト試行回数を増やすということは抜けを見つける確率を上げる方法として正しいが、スクリプトを組んで探索範囲を複数に分けて複数のコアで回せばより早くなるしそうしたほうが工夫した点や今後の課題で書きやすいから考えてみて」と言われました。
自分はスクリプトというものを今まで組んだことがないのですが、書き方等をご教授願えないでしょうか?
今は上のプログラムに対して
*Main Lib> quickCheck $ forAll (choose(5,100)) $ test_bounce
と入力して初期位置が5以上100以下のものからランダムに100パターン、1000000サイクル×0.01秒後の位置が-1未満(地面を貫通しているか)で判定しているのですが、
教授の言うスクリプトというものは
①二つに分ける場合、初期位置等を5-50と50-100に分けておこなう
②それぞれ別のコアで行う
を行えるようにすることだと思うのですが、具体的にスクリプトがどのように行うものかも含めて教えてくれるとありがたいです
ここでいう「スクリプト」が本来プログラマが常用している「スクリプト」と同じものを指しているかわかりませんが、要するに先生が言っていることって「Yampa の QuickCheck を並列実行してみれば?」という話ですよね?
自分はスクリプトというものを今まで組んだことがないのですが、書き方等をご教授願えないでしょうか?

取り急ぎ。普通「スクリプト」という時は単に「小さなプログラム」ぐらいの意味しかないです。ので、そういうプログラムを書いてみて、という話ではないかと。
Yampa の QuickCheck を並列実行を行うことだと思います。
QuickCheckを並列実行を一つの端末画面で行うためにスクリプトを組んでねという感じだと思います。
それで自分はそもそもQuickCheckの並列実行を一つの端末画面で行う方法がわからない&スクリプトを何で書けばいいのか&stack ghci上で行うのか等がわかっていない状況です
「2つのテストケースを並列に実行する関数を書いてね」だったらhspec + quickcheckでなんとかなりそうだけど。
https://hspec.github.io/parallel-spec-execution.html
パラメーターの範囲ごとにテストケースを分ければそれでいけそうですね。
あと、途中経過を表示させなくてもよければ、単純に

quickCheckWithResult stdArgs { chatty = False } prop


という関数を async などを使って並列に実行するのでもよいかと思います。
スレッドごとにパラメーターの範囲が変わるよう調整すれば、要件が満たせるでしょう。

あと、自分で結果を出力する必要がありますが...
ありがとうございます!Parallel spec executionで試してみます。
お二人方とも回答ありがとうございました! igrep さんの方法でやってみます!
@ has joined the channel
@白椿 has joined the channel
@ has joined the channel
@yantene has joined the channel