如何连接哈希映射中的值?
How to join values from hash-maps?
我通过 JDBC 获取了一些 SQL table,我需要在创建新的 table 和插入值之前进行另一次转换。
我得到了这两个哈希映射:
章节:
(
{:chapter_uuid "b7984dde-50a1-4147-bfee-95bbd068e031", :l1_chapter_text
120876M, :l2_chapter_text nil, :l3_chapter_text nil, :l4_chapter_text nil}
{:chapter_uuid "23df4f27-534b-4cdb-81ed-dbdc8b9b140c", :l1_chapter_text
120880M, :l2_chapter_text 120876M, :l3_chapter_text nil, :l4_chapter_text
121621M}
)
翻译:
(
{:translation_id 3258779M, :translation_text 120876M, :translation_language "cs",
:translation_name "Vnější fasáda"}
{:translation_id 3258780M, :translation_text 120876M, :translation_language "en",
:translation_name "Exterior Signage"}
{:translation_id 3258782M, :translation_text 120880M, :translation_language "cs",
:translation_name "Čistá výloha"}
{:translation_id 3258783M, :translation_text 121621M, :translation_language "cs",
:translation_name "Vnější signalizace"}
{:translation_id 3258784M, :translation_text 121621M, :translation_language "en",
:translation_name "Pre-signalization"}
)
这是我需要得到的:
其中 Chapters.lx_chapter_text = Translation.translation_text -> 将 Chapters.lx_chapter_text 替换为 translation_name 并插入:语言值 -> 确保每种语言都有其自己的哈希映射!
(
{:chapter_uuid "b7984dde-50a1-4147-bfee-95bbd068e031", :l1_chapter_text
"Vnější fasáda", :l2_chapter_text nil, :l3_chapter_text nil, :l4_chapter_text nil
:language "cs"}
{:chapter_uuid "b7984dde-50a1-4147-bfee-95bbd068e031", :l1_chapter_text
"Exterior Signage", :l2_chapter_text nil, :l3_chapter_text nil, :l4_chapter_text nil
:language "en"}
{:chapter_uuid "23df4f27-534b-4cdb-81ed-dbdc8b9b140c", :l1_chapter_text
"Čistá výloha", :l2_chapter_text "Vnější fasáda", :l3_chapter_text nil, :l4_chapter_text
"Vnější signalizace" :language "cs"}
{:chapter_uuid "23df4f27-534b-4cdb-81ed-dbdc8b9b140c", :l1_chapter_text
120880M, :l2_chapter_text "Exterior Signage", :l3_chapter_text nil, :l4_chapter_text
"Pre-signalization" :language "en"}
)
这是我的进度:
但如您所见,这是不正确的(嵌套错误)
你能告诉我正确的做法吗?谢谢!
(defn test_table []
(for [language (distinct(map #(:translation_language %) translation))]
(for [chapter chapters]
(for [text translation]
(cond
(and (= (:l1_chapter_text chapter) (:translation_text text)) (= (:translation_language text) language))
(assoc chapter :l1_chapter_text (:translation_name text) :language (:translation_language text))
(and (= (:l2_chapter_text chapter) (:translation_text text)) (= (:translation_language text) language))
(assoc chapter :l2_chapter_text (:translation_name text) :language (:translation_language text))
(and (= (:l3_chapter_text chapter) (:translation_text text)) (= (:translation_language text) language))
(assoc chapter :l3_chapter_text (:translation_name text) :language (:translation_language text))
(and (= (:l4_chapter_text chapter) (:translation_text text)) (= (:translation_language text) language))
(assoc chapter :l4_chapter_text (:translation_name text) :language (:translation_language text))))))
(test-table)
->
((({:chapter_uuid "b7984dde-50a1-4147-bfee-95bbd068e031", :l1_chapter_text "Vnější fasáda",
:l2_chapter_text nil, :l3_chapter_text nil, :l4_chapter_text nil, :language "cs"}
nil nil nil nil)
({:chapter_uuid "23df4f27-534b-4cdb-81ed-dbdc8b9b140c", :l1_chapter_text 120880M,
:l2_chapter_text "Vnější fasáda", :l3_chapter_text nil, :l4_chapter_text 121621M, :language "cs"}
nil
{:chapter_uuid "23df4f27-534b-4cdb-81ed-dbdc8b9b140c", :l1_chapter_text "Čistá výloha",
:l2_chapter_text 120876M, :l3_chapter_text nil, :l4_chapter_text 121621M, :language "cs"}
{:chapter_uuid "23df4f27-534b-4cdb-81ed-dbdc8b9b140c", :l1_chapter_text 120880M,
:l2_chapter_text 120876M, :l3_chapter_text nil, :l4_chapter_text "Vnější signalizace", :language "cs"}
nil))
((nil
{:chapter_uuid "b7984dde-50a1-4147-bfee-95bbd068e031", :l1_chapter_text "Exterior Signage",
:l2_chapter_text nil, :l3_chapter_text nil, :l4_chapter_text nil, :language "en"}
nil nil nil)
(nil
{:chapter_uuid "23df4f27-534b-4cdb-81ed-dbdc8b9b140c", :l1_chapter_text 120880M,
:l2_chapter_text "Exterior Signage", :l3_chapter_text nil, :l4_chapter_text 121621M, :language "en"}
nil nil
{:chapter_uuid "23df4f27-534b-4cdb-81ed-dbdc8b9b140c", :l1_chapter_text 120880M,
:l2_chapter_text 120876M, :l3_chapter_text nil, :l4_chapter_text "Pre-signalization", :language "en"})))
首先,您是否有翻译中使用的所有语言的列表?如果不是,让我们从 translations
集合中导出它:
(def langs (distinct (map :translation_language translations))) ;; => ("cs" "en")
其次,由于您将使用 translations
集合作为查找 table,因此制作它的地图是有意义的。最简单(虽然可能不是最有效)的方法是使用 group-by
函数:
(def translations-map
(group-by (juxt :translation_text :translation_language) translations))
看起来您需要做的是将每个 :l<#>_chapter_text
转换为实际文本,或者如果给定语言的翻译不可用,则保留 ID。使用我们创建的地图,这几乎是微不足道的:
(defn translate [id lang]
(or (:translation_name (first (get translations-map [id lang])))
id))
现在,让我们把它们放在一起,对每个 chapter
并针对每种语言,尝试用翻译替换所有 ID:
(for [chapter chapters
lang langs]
(-> chapter
(assoc :language lang)
(update :l1_chapter_text translate lang)
(update :l2_chapter_text translate lang)
(update :l3_chapter_text translate lang)
(update :l4_chapter_text translate lang)))
这应该 return 想要的结果。
(let [a ...
b ...]
(as-> [:l1_chapter_text :l2_chapter_text :l3_chapter_text :l4_chapter_text]
relations
(interleave relations (repeat :translation_text))
(apply hash-map relations)
(mapcat #(clojure.set/join a b (into {} [%])) relations)
(group-by (fn [a] (apply str ((juxt :chapter_uuid :l1_chapter_text :l2_chapter_text :l3_chapter_text :l4_chapter_text :translation_language) a))) relations)
(vals relations)))
我通过 JDBC 获取了一些 SQL table,我需要在创建新的 table 和插入值之前进行另一次转换。
我得到了这两个哈希映射:
章节:
(
{:chapter_uuid "b7984dde-50a1-4147-bfee-95bbd068e031", :l1_chapter_text
120876M, :l2_chapter_text nil, :l3_chapter_text nil, :l4_chapter_text nil}
{:chapter_uuid "23df4f27-534b-4cdb-81ed-dbdc8b9b140c", :l1_chapter_text
120880M, :l2_chapter_text 120876M, :l3_chapter_text nil, :l4_chapter_text
121621M}
)
翻译:
(
{:translation_id 3258779M, :translation_text 120876M, :translation_language "cs",
:translation_name "Vnější fasáda"}
{:translation_id 3258780M, :translation_text 120876M, :translation_language "en",
:translation_name "Exterior Signage"}
{:translation_id 3258782M, :translation_text 120880M, :translation_language "cs",
:translation_name "Čistá výloha"}
{:translation_id 3258783M, :translation_text 121621M, :translation_language "cs",
:translation_name "Vnější signalizace"}
{:translation_id 3258784M, :translation_text 121621M, :translation_language "en",
:translation_name "Pre-signalization"}
)
这是我需要得到的:
其中 Chapters.lx_chapter_text = Translation.translation_text -> 将 Chapters.lx_chapter_text 替换为 translation_name 并插入:语言值 -> 确保每种语言都有其自己的哈希映射!
(
{:chapter_uuid "b7984dde-50a1-4147-bfee-95bbd068e031", :l1_chapter_text
"Vnější fasáda", :l2_chapter_text nil, :l3_chapter_text nil, :l4_chapter_text nil
:language "cs"}
{:chapter_uuid "b7984dde-50a1-4147-bfee-95bbd068e031", :l1_chapter_text
"Exterior Signage", :l2_chapter_text nil, :l3_chapter_text nil, :l4_chapter_text nil
:language "en"}
{:chapter_uuid "23df4f27-534b-4cdb-81ed-dbdc8b9b140c", :l1_chapter_text
"Čistá výloha", :l2_chapter_text "Vnější fasáda", :l3_chapter_text nil, :l4_chapter_text
"Vnější signalizace" :language "cs"}
{:chapter_uuid "23df4f27-534b-4cdb-81ed-dbdc8b9b140c", :l1_chapter_text
120880M, :l2_chapter_text "Exterior Signage", :l3_chapter_text nil, :l4_chapter_text
"Pre-signalization" :language "en"}
)
这是我的进度:
但如您所见,这是不正确的(嵌套错误)
你能告诉我正确的做法吗?谢谢!
(defn test_table []
(for [language (distinct(map #(:translation_language %) translation))]
(for [chapter chapters]
(for [text translation]
(cond
(and (= (:l1_chapter_text chapter) (:translation_text text)) (= (:translation_language text) language))
(assoc chapter :l1_chapter_text (:translation_name text) :language (:translation_language text))
(and (= (:l2_chapter_text chapter) (:translation_text text)) (= (:translation_language text) language))
(assoc chapter :l2_chapter_text (:translation_name text) :language (:translation_language text))
(and (= (:l3_chapter_text chapter) (:translation_text text)) (= (:translation_language text) language))
(assoc chapter :l3_chapter_text (:translation_name text) :language (:translation_language text))
(and (= (:l4_chapter_text chapter) (:translation_text text)) (= (:translation_language text) language))
(assoc chapter :l4_chapter_text (:translation_name text) :language (:translation_language text))))))
(test-table)
->
((({:chapter_uuid "b7984dde-50a1-4147-bfee-95bbd068e031", :l1_chapter_text "Vnější fasáda",
:l2_chapter_text nil, :l3_chapter_text nil, :l4_chapter_text nil, :language "cs"}
nil nil nil nil)
({:chapter_uuid "23df4f27-534b-4cdb-81ed-dbdc8b9b140c", :l1_chapter_text 120880M,
:l2_chapter_text "Vnější fasáda", :l3_chapter_text nil, :l4_chapter_text 121621M, :language "cs"}
nil
{:chapter_uuid "23df4f27-534b-4cdb-81ed-dbdc8b9b140c", :l1_chapter_text "Čistá výloha",
:l2_chapter_text 120876M, :l3_chapter_text nil, :l4_chapter_text 121621M, :language "cs"}
{:chapter_uuid "23df4f27-534b-4cdb-81ed-dbdc8b9b140c", :l1_chapter_text 120880M,
:l2_chapter_text 120876M, :l3_chapter_text nil, :l4_chapter_text "Vnější signalizace", :language "cs"}
nil))
((nil
{:chapter_uuid "b7984dde-50a1-4147-bfee-95bbd068e031", :l1_chapter_text "Exterior Signage",
:l2_chapter_text nil, :l3_chapter_text nil, :l4_chapter_text nil, :language "en"}
nil nil nil)
(nil
{:chapter_uuid "23df4f27-534b-4cdb-81ed-dbdc8b9b140c", :l1_chapter_text 120880M,
:l2_chapter_text "Exterior Signage", :l3_chapter_text nil, :l4_chapter_text 121621M, :language "en"}
nil nil
{:chapter_uuid "23df4f27-534b-4cdb-81ed-dbdc8b9b140c", :l1_chapter_text 120880M,
:l2_chapter_text 120876M, :l3_chapter_text nil, :l4_chapter_text "Pre-signalization", :language "en"})))
首先,您是否有翻译中使用的所有语言的列表?如果不是,让我们从 translations
集合中导出它:
(def langs (distinct (map :translation_language translations))) ;; => ("cs" "en")
其次,由于您将使用 translations
集合作为查找 table,因此制作它的地图是有意义的。最简单(虽然可能不是最有效)的方法是使用 group-by
函数:
(def translations-map
(group-by (juxt :translation_text :translation_language) translations))
看起来您需要做的是将每个 :l<#>_chapter_text
转换为实际文本,或者如果给定语言的翻译不可用,则保留 ID。使用我们创建的地图,这几乎是微不足道的:
(defn translate [id lang]
(or (:translation_name (first (get translations-map [id lang])))
id))
现在,让我们把它们放在一起,对每个 chapter
并针对每种语言,尝试用翻译替换所有 ID:
(for [chapter chapters
lang langs]
(-> chapter
(assoc :language lang)
(update :l1_chapter_text translate lang)
(update :l2_chapter_text translate lang)
(update :l3_chapter_text translate lang)
(update :l4_chapter_text translate lang)))
这应该 return 想要的结果。
(let [a ...
b ...]
(as-> [:l1_chapter_text :l2_chapter_text :l3_chapter_text :l4_chapter_text]
relations
(interleave relations (repeat :translation_text))
(apply hash-map relations)
(mapcat #(clojure.set/join a b (into {} [%])) relations)
(group-by (fn [a] (apply str ((juxt :chapter_uuid :l1_chapter_text :l2_chapter_text :l3_chapter_text :l4_chapter_text :translation_language) a))) relations)
(vals relations)))