【问题标题】:"Crossed" sums between two vectors两个向量之间的“交叉”和
【发布时间】:2016-03-20 15:01:35
【问题描述】:

我有两个这样的向量(或集合,没关系): [1 2 3...

我们说

(def v (range 1 4))

我想计算这个向量的“交叉”和。 我的意思是对于 v 中的每个 x,计算它与 v 的每个值的总和。

假设向量是 [1 2 3],我想要一个这样的矩阵:

    (1)(2)(3)
(1)  2  3  4
(2)  3  4  5
(3)  4  5  6

我不知道我是否清楚,但我没有看到任何 Clojure 函数可以做到这一点。 我会考虑递归或排列,但它似乎不是很地道。

有什么想法吗?

谢谢!

编辑

计算“交叉”总和的代码示例(仅当数字不同时),在 mod n 处减少总和,然后计算关于它的统计数据

(defn crossed-sum [n]
  (let [v (range 1 (+ n 1))]
    (mapcat
      (fn [x]
        (for [k v
              :let [y (cond (= k x)
                              -1
                            :else
                              (+ k x))]]
          y))
      v)))

(defn mod-reduc [data n]
  (map
    (fn [x]
      (rem x n))
    data))


(defn compute-probability [n]
  (let [c-sum (-> (crossed-sum n)
                  (mod-reduc n)
                  (frequencies)
                  (dissoc -1))
        s (reduce + (vals c-sum))]
    (apply conj (map
                  (fn [[k v]]
                    {k (float (/ v s))})
                 c-sum))))

我使用了for,但它是惯用的吗?

【问题讨论】:

    标签: clojure


    【解决方案1】:

    此函数生成列表列表(代替矩阵),就像您在示例中描述的那样。

    (defn cross-add [v]
        (for [number v]
          (map #(+ number %)
               v)))
    

    例子:

    user> (cross-add [1 2 3])
    ((2 3 4) (3 4 5) (4 5 6))
    
    user> (cross-add [5 13 8 9 12])
    ((10 18 13 14 17) (18 26 21 22 25) (13 21 16 17 20) (14 22 17 18 21) (17 25 20 21 24))
    

    【讨论】:

    • 也谢谢,我忘了我要了一份清单!我可以用 ma 代替 mapcat
    【解决方案2】:

    顺便说一句,range 返回惰性序列,而不是向量。但是,这里不重要。

    使用for 就够了。

    (let [numbers (range 1 4)]
      (for [n numbers
            m numbers]
        (+ n m)))
    ;; -> (2 3 4 3 4 5 4 5 6)
    

    如果你只想计算不同的数字,你可以这样写。

    (let [numbers (range 1 4)]
      (for [n numbers
            m numbers
            :when (not= n m)]
        (+ n m)))
    ;; -> (3 4 3 5 4 5)
    

    【讨论】:

    • 真的不知道要接受什么答案,因为两者都有输入,但在这里我学到了 :when 条件,在可读性方面比 cond 好得多。对于列表列表,我可以使用 map 而不是 mapcat。是的,向量不是强制性的,我这样说是因为我更喜欢数学语言
    猜你喜欢
    • 1970-01-01
    • 2018-06-22
    • 1970-01-01
    • 2018-01-21
    • 1970-01-01
    • 1970-01-01
    • 2013-12-04
    • 1970-01-01
    • 2015-04-27
    相关资源
    最近更新 更多