在Clojure中获取最大值和最小值

Pau*_*aul 1 clojure max min

我试图将SQL查询的最大和最小结果拉到Clojure中,这样我就可以对它们进行数学分析,但我不确定为什么会出现错误.

我已经在代码中使用了max和min函数来尝试确定这些结果,尽管我一直收到两个错误,这些错误似乎与我使用:counter关键字的方式有关.

从SQL查询的映射中返回的数据如下所示:

    {:date1 "20131007", :data "object1", :counter 1000}
    {:date1 "20131007", :data "object2", :counter 50}
    {:date1 "20131007", :data "object3", :counter 230}
Run Code Online (Sandbox Code Playgroud)

当我使用这段代码时:

    minvalue(min(map(keyword :counter)data2))
    maxvalue(max(map(keyword :counter)data2))
    valrange(- maxvalue minvalue)
    valpc(* (/ valrange 100) 10)
    x(- maxvalue valpc)
Run Code Online (Sandbox Code Playgroud)

我显然希望将minvalue设置为50并将maxvalue设置为1000,尽管我收到此错误:

    java.lang.ClassCastException: clojure.lang.LazySeq cannot be cast to java.lang.Number
Run Code Online (Sandbox Code Playgroud)

如果我从代码中删除map函数并再次运行它,我收到此错误:

    java.lang.ClassCastException: clojure.lang.Keyword cannot be cast to java.lang.Number
Run Code Online (Sandbox Code Playgroud)

任何帮助都是值得赞赏的,因为我完全陷入了困境(而且我可能是Clojure的新手)谢谢

sta*_*203 6

您的代码有一些变化:

  • min和max采用可变数量的参数,而不是集合.使用apply,将集合的内容应用为参数.
  • Clojure命名约定使用 - 在单词之间
  • 有效的调用必须是一个表单(基本上是第一个项目可调用的列表)
  • 无需使用"关键字",关键字适用于有字符串且需要关联关键字的情况.对于从地图中拖出数据,关键字充当函数本身,例如(:a {:a 1:b 2})返回1.
  • 考虑到前两行中的共性

    (def data [{:date1 "20131007", :data "object1", :counter 1000}
               {:date1 "20131007", :data "object2", :counter 50}
               {:date1 "20131007", :data "object3", :counter 230}])
    
    (def counters (map :counter data))      ; => (100 50 230)
    (def min-value (apply min counters))    ; => 50
    (def max-value (apply max counters))    ; => 1000
    (def val-range (- max-value min-value)) ; => 950
    (def val-pc (* (/ val-range 100) 10))   ; => 95
    (def x (- max-value val-pc))            ; => 905
    
    Run Code Online (Sandbox Code Playgroud)


def*_*hlt 5

user=> data
[{:data "object1", :date1 "20131007", :counter 1000} {:data "object2", :date1 "20131007", :counter 50} {:data "object3", :date1 "20131007", :counter 230}]

user=> (apply max-key :counter data)
{:data "object1", :date1 "20131007", :counter 1000}

user=> (apply min-key :counter data)
{:data "object2", :date1 "20131007", :counter 50}
Run Code Online (Sandbox Code Playgroud)