基于用户输入的增量和 return 数字
Increment and return number based on user input
所以我有一个问题向量,想根据用户的输入递增 return 一个数字。这给我带来了麻烦,我认为这是因为缺乏对 Clojure 及其理想的理解。这是我得到的最接近的值,但我得到的 returned 是 0.
(defn print-questions [questions]
(let [number 0]
(doseq [question questions]
(println question)
(let [x (read-line)]
(if (= (.toLowerCase x) "y")
(inc number)
(println "No"))))
number))
Clojure 不会像您在命令式语言中遇到的那样使用变量,因此像 (inc x) return 这样的语句是一个比 x 高 1 的新值,而单独保留 x而不是就地改变 x。
写这段代码意味着:
(defn print-questions [questions]
(let [number 0]
;; start with zero every time
;; don't carry any information forward between iterations of the loop
(doseq [question questions]
(println question)
(let [x (read-line)]
(if (= (.toLowerCase x) "y")
(inc number) ;; this DOES NOT change the value in number
(println "No"))))
number)) ;; when you are all done, return the original value of number
这对于许多线程处理相同数据的情况非常有用,尽管它确实会导致看待事物的方式有所不同。
编写非常相似的内容的一种方法是循环遍历问题,同时将每次迭代的数字的当前值传递给下一次迭代,如下所示:
user=> (defn print-questions [questions]
#_=> (loop [number 0 remaining-questions questions]
#_=> (println remaining-questions)
#_=> (if (seq remaining-questions)
#_=> (let [x (read-line)]
#_=> (if (= x "y")
#_=> (do (println "yes")
#_=> (recur (inc number) (rest remaining-questions)))
#_=> (do (println "No")
#_=> (recur number (rest remaining-questions)))))
#_=> number)))
#'user/print-questions
user=> (print-questions ["who" "what" "when" "why"])
[who what when why]
y
yes
(what when why)
y
yes
(when why)
n
No
(why)
y
yes
()
3
虽然有点冗长,但有效。相反,如果我们将其视为将问题集合缩减为一个数字,其中每个缩减阶段都将其中一个零添加到结果中,那么它会更加紧凑:
user=> (defn print-questions [questions]
#_=> (reduce (fn [answer question]
#_=> (println question)
#_=> (if (= "y" (read-line))
#_=> (inc answer)
#_=> answer))
#_=> 0
#_=> questions))
#'user/print-questions
user=> (print-questions ["who" "what" "when" "why"])
who
y
what
n
when
y
why
y
3
reduce 采用一个函数来完成实际工作、一个开始的值和一个输入列表。然后它使用具有第一个值的函数来创建新结果,然后使用具有第二个值的函数来产生新结果,第三个等等,直到输入中的每个值都有机会影响最终结果。
所以我有一个问题向量,想根据用户的输入递增 return 一个数字。这给我带来了麻烦,我认为这是因为缺乏对 Clojure 及其理想的理解。这是我得到的最接近的值,但我得到的 returned 是 0.
(defn print-questions [questions]
(let [number 0]
(doseq [question questions]
(println question)
(let [x (read-line)]
(if (= (.toLowerCase x) "y")
(inc number)
(println "No"))))
number))
Clojure 不会像您在命令式语言中遇到的那样使用变量,因此像 (inc x) return 这样的语句是一个比 x 高 1 的新值,而单独保留 x而不是就地改变 x。
写这段代码意味着:
(defn print-questions [questions]
(let [number 0]
;; start with zero every time
;; don't carry any information forward between iterations of the loop
(doseq [question questions]
(println question)
(let [x (read-line)]
(if (= (.toLowerCase x) "y")
(inc number) ;; this DOES NOT change the value in number
(println "No"))))
number)) ;; when you are all done, return the original value of number
这对于许多线程处理相同数据的情况非常有用,尽管它确实会导致看待事物的方式有所不同。
编写非常相似的内容的一种方法是循环遍历问题,同时将每次迭代的数字的当前值传递给下一次迭代,如下所示:
user=> (defn print-questions [questions]
#_=> (loop [number 0 remaining-questions questions]
#_=> (println remaining-questions)
#_=> (if (seq remaining-questions)
#_=> (let [x (read-line)]
#_=> (if (= x "y")
#_=> (do (println "yes")
#_=> (recur (inc number) (rest remaining-questions)))
#_=> (do (println "No")
#_=> (recur number (rest remaining-questions)))))
#_=> number)))
#'user/print-questions
user=> (print-questions ["who" "what" "when" "why"])
[who what when why]
y
yes
(what when why)
y
yes
(when why)
n
No
(why)
y
yes
()
3
虽然有点冗长,但有效。相反,如果我们将其视为将问题集合缩减为一个数字,其中每个缩减阶段都将其中一个零添加到结果中,那么它会更加紧凑:
user=> (defn print-questions [questions]
#_=> (reduce (fn [answer question]
#_=> (println question)
#_=> (if (= "y" (read-line))
#_=> (inc answer)
#_=> answer))
#_=> 0
#_=> questions))
#'user/print-questions
user=> (print-questions ["who" "what" "when" "why"])
who
y
what
n
when
y
why
y
3
reduce 采用一个函数来完成实际工作、一个开始的值和一个输入列表。然后它使用具有第一个值的函数来创建新结果,然后使用具有第二个值的函数来产生新结果,第三个等等,直到输入中的每个值都有机会影响最终结果。