在Elm中生成随机数所需的最少代码是什么?

3
我只是想看到一个随机数。因此,这里有一个直接从文档中摘出的Random库的示例。我期望Random.generate接受一个生成器和一个种子,并返回一个包含随机值和新种子的元组,如下所示:

generate : Generator a -> Seed -> (a, Seed)

-- Main.elm

import Random

seed0 = Random.initialSeed 31415
randomNumber = Random.generate (Random.int 0 10) seed0
main = 
  -- print result of randomNumber here

编译器错误显示了两个类型不匹配问题:
-- TYPE MISMATCH ---------------------------------------------------- -----------

The 2nd argument to function `generate` is causing a mismatch.

5|        Random.generate (Random.int 0 10) seed0
                                        ^^^^^
Function `generate` is expecting the 2nd argument to be:

    Random.Generator a

But it is:

    Random.Seed


The 1st argument to function `generate` is causing a mismatch.

5|        Random.generate (Random.int 0 10) seed0
                       ^^^^^^^^^^^^^^^
Function `generate` is expecting the 1st argument to be:

    a -> b

But it is:

    Random.Generator Int

我在这里缺少什么?

http://elm-lang.org/examples/random - Tosh
我真的需要一个完整的elm应用程序才能看到一个随机数的实例吗?换句话说,我的问题是“我可以从您刚刚发布的示例中删除多少内容而不会出现类型错误?” - Joseph Fraley
3个回答

4

您所参考的文档版本是Core 1.0.0,已经过时。当前版本为Core 4.0.5。(这里是Random的文档

您正在寻找的函数现在被命名为step

step : Generator a -> Seed -> (a, Seed)

所以,您重构后的代码应该像这样:

因此,您重新设计的代码应该类似于:

import Html exposing (text)
import Random

seed0 = Random.initialSeed 31415
(randomNumber, nextSeed) = Random.step (Random.int 0 10) seed0

main =
  text <| toString randomNumber

2
这正是问题所在。我应该向Gitbook提交PR以更新他们的文档链接。谢谢! - Joseph Fraley

3

这是我能想到的最简单的例子。 因为它提供了固定的种子,因此它将返回相同的布尔值。

如果你需要在运行时生成随机数,则必须使用 Random.generate,它会产生 Cmd,以便 Elm 运行时可以获得随机性。 在这种情况下,需要某种形式的 Platform.Program,因为它是运行 Cmd 的唯一方式。

import Html exposing (text)
import Random exposing (..)

main =
  text <| toString <| Tuple.first <| step bool (initialSeed 1)

2

Elm 2022(v0.19)答案:

这是一个在Elm 0.19.1中生成0到1000之间数字的绝对最小示例,可运行的Ellie示例依赖于elm/random。通常情况下,您不会在代码中使用大量()符号,而是使用MsgModel,但考虑到代码最小化的原则,此处采用了上述方式。

module Main exposing (main)

import Browser
import Html
import Random


view : () -> Html.Html ()
view model =
    let
        -- this generates the rng number
        generator =
            Random.int 0 1000

        -- used to seed the generator
        seed =
            Random.initialSeed 12345

        -- Random.step returns the generated value, and a new seed.
        -- Usually you store the newSeed on your model so you don't always generate the same value
        ( value, newSeed ) =
            Random.step
                generator
                seed
    in
    Html.text <| String.fromInt value


main : Program () () ()
main =
    Browser.sandbox
        { init = ()
        , view = view
        , update = \msg model -> model
        }

其他最佳实践包括在模型上存储一些全局种子:

type alias Model = { globalSeed : Random.Seed }

然后在使用它并更新模型上的内容之后:

update : Msg -> Model -> (Model, Cmd.none)
update msg model =
    case msg of
       GenerateValue ->
          let
             (newValue, newSeed) =
               Random.step (Random.int 0 1000) model.globalSeed

             _ =
               Debug.log "generated a new value" newValue

          in
          ( {model | globalSeed = newSeed}, Cmd.none)

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接