Clojure-da xarita indekslari va vektor yordamida formatlash

I am trying to read content from a file which is in the format :

ID|Name|Country-Name|Phone-Number eg:

1|Austin|Germany|34-554567
2|Mary Jane|Australia|45-78647

Ma'lumotlardan foydalanish uchun quyidagi kodni ishlataman:

(
  map-indexed
    #(vector %1 %2)
    (
      map #(vec(.split #"\|" %1))
      (
        line-seq (clojure.java.io/reader "test.txt")
      )
    )
)

Ushbu kod bilan men ushbu mahsulotni olaman:

([0 ["1" "Austin" "Germany" "34-554567"]] [1 ["2" "Mary Jane" "Australia" "45-78647"]] [2 ["3" "King Kong" "New-Zealand" "35-467533"]])

Chiqish shunday bo'lishini xohlayman:

ID:["name" "country-name" "phone-number"]
ID:["name" "country-name" "phone-number"]

eg:

1:["Austin" "Germany" "34-554567"]
2:["Mary Jane" "Australia" "45-78647"]

ID ga 1 (1,2,3 dan boshlang va hokazo) boshlang va har bir natija identifikator bilan birlashtirilgan ma'lumotlarning muvaffaqiyatli identifikatorini yoki identifikatorini ro'yxatlang va ID bilan tartiblash kerak.

Buni amalga oshirish uchun kodimga qanday o'zgarishlar kiritaman?

0
so'ragan narsangizga o'xshash narsaga o'xshaydi.
qo'shib qo'ydi muallif manandearth, manba
ID tomonidan kiritilgan xaritani yaratmoqchimisiz? (sizning chiqishingiz) ga ishlating.
qo'shib qo'ydi muallif Hendrik Poernama, manba
Ha, men o'z matn faylimdagi identifikator raqamini chiqim sifatida olgan narsaga belgilashga harakat qilaman. Shunday qilib, men ularni oxirigacha osonlashtiraman
qo'shib qo'ydi muallif Prishu, manba
Ha, men o'z matn faylimdagi identifikator raqamini chiqim sifatida olgan narsaga belgilashga harakat qilaman. Shunday qilib, men ularni oxirigacha osonlashtiraman
qo'shib qo'ydi muallif Prishu, manba
Darhaqiqat, aslida hozirgi paytda mening haqiqiy chiqishga mos emas. Bundan tashqari, men hamma narsani vektor sifatida belgilash va har bir qadriyatni o'z ko'rsatkichlari bilan olishni juda qiyin deb bilaman
qo'shib qo'ydi muallif Prishu, manba
Darhaqiqat, aslida hozirgi paytda mening haqiqiy chiqishga mos emas. Bundan tashqari, men hamma narsani vektor sifatida belgilash va har bir qadriyatni o'z ko'rsatkichlari bilan olishni juda qiyin deb bilaman
qo'shib qo'ydi muallif Prishu, manba

5 javoblar

Sizning ma'lumotlaringiz indekslar allaqachon mavjud kabi ko'rinadi:

(def data
  "1|Austin|Germany|34-554567
   2|Mary Jane|Australia|45-78647
   3|King Kong|New-Zealand|35-467533 ")

(defn fmt [line]
  (let [sections (-> line
                     str/trim
                     (str/split #"\|")) ]
    sections) )

(defn run []
  (let [lines (vec (str/split-lines data)) ]
    (mapv fmt lines)))

(run)

natijasi:

sections => ["1" "Austin" "Germany" "34-554567"]
sections => ["2" "Mary Jane" "Australia" "45-78647"]
sections => ["3" "King Kong" "New-Zealand" "35-467533"]

Agar ma'lumotlar indekslarini tashlab qo'ymoqchi bo'lsangiz, o'zingizning shunga o'xshash tarzda yaratasiz:

(defn fmt [idx line]
  (let [sections      (-> line
                          str/trim
                          (str/split #"\|"))
        sections-keep (rest sections)
        result        (apply vector idx sections-keep)]
    result))

(defn run []
  (let [lines (vec (str/split-lines data))]
    (mapv fmt (range 1 1e9) lines)))

Yangilash

Disk fayllaridan foydalanmoqchi bo'lsangiz, buni bajaring:

(def data
  "1|Austin|Germany|34-554567
   2|Mary Jane|Australia|45-78647
   3|King Kong|New-Zealand|35-467533 ")

(defn fmt [idx line]
  (let [sections      (-> line
                          str/trim
                          (str/split #"\|"))
        sections-keep (rest sections)
        result        (apply vector idx sections-keep)]
    result))

(defn run [filename]
  (let [lines (vec (str/split-lines (slurp filename)))]
    (mapv fmt (range 1 1e9) lines)))

(let [filename "/tmp/demo.txt"]
  (spit filename data)
  (run filename))
0
qo'shib qo'ydi
Men faylni yaratishni ko'rsatish uchun faqat tupni ni qo'shdim. Agar sizda bo'lsa, bunga muhtoj emassiz.
qo'shib qo'ydi muallif Alan Thompson, manba
Yangilangan javoblaringizda men tushundim. Siz demo.txt deb nomlangan faylga ma'lumotni qo'yishga harakat qilyapsiz va keyin o'sha faylni slurp orqali o'qishingiz mumkin. Fmt funktsiyasida siz trim va split operatsiyalarini qo'lladingiz, keyin esa fmt-ni argument sifatida qabul qilib, sizning xaritalash vektoringizdir. Agar noto'g'ri bo'lsam, iltimos meni to'g'rilab qo'ying. Aytgancha, menda ma'lumotlar o'qigan joydan fayl bor. demo.txt ko'rsatilgandek yangi oyna yaratish zarurati bormi? Boshim ustidan g'alaba qozonadigan narsalar.
qo'shib qo'ydi muallif Prishu, manba

Sizning ma'lumotlaringiz indekslar allaqachon mavjud kabi ko'rinadi:

(def data
  "1|Austin|Germany|34-554567
   2|Mary Jane|Australia|45-78647
   3|King Kong|New-Zealand|35-467533 ")

(defn fmt [line]
  (let [sections (-> line
                     str/trim
                     (str/split #"\|")) ]
    sections) )

(defn run []
  (let [lines (vec (str/split-lines data)) ]
    (mapv fmt lines)))

(run)

natijasi:

sections => ["1" "Austin" "Germany" "34-554567"]
sections => ["2" "Mary Jane" "Australia" "45-78647"]
sections => ["3" "King Kong" "New-Zealand" "35-467533"]

Agar ma'lumotlar indekslarini tashlab qo'ymoqchi bo'lsangiz, o'zingizning shunga o'xshash tarzda yaratasiz:

(defn fmt [idx line]
  (let [sections      (-> line
                          str/trim
                          (str/split #"\|"))
        sections-keep (rest sections)
        result        (apply vector idx sections-keep)]
    result))

(defn run []
  (let [lines (vec (str/split-lines data))]
    (mapv fmt (range 1 1e9) lines)))

Yangilash

Disk fayllaridan foydalanmoqchi bo'lsangiz, buni bajaring:

(def data
  "1|Austin|Germany|34-554567
   2|Mary Jane|Australia|45-78647
   3|King Kong|New-Zealand|35-467533 ")

(defn fmt [idx line]
  (let [sections      (-> line
                          str/trim
                          (str/split #"\|"))
        sections-keep (rest sections)
        result        (apply vector idx sections-keep)]
    result))

(defn run [filename]
  (let [lines (vec (str/split-lines (slurp filename)))]
    (mapv fmt (range 1 1e9) lines)))

(let [filename "/tmp/demo.txt"]
  (spit filename data)
  (run filename))
0
qo'shib qo'ydi
Men faylni yaratishni ko'rsatish uchun faqat tupni ni qo'shdim. Agar sizda bo'lsa, bunga muhtoj emassiz.
qo'shib qo'ydi muallif Alan Thompson, manba
Yangilangan javoblaringizda men tushundim. Siz demo.txt deb nomlangan faylga ma'lumotni qo'yishga harakat qilyapsiz va keyin o'sha faylni slurp orqali o'qishingiz mumkin. Fmt funktsiyasida siz trim va split operatsiyalarini qo'lladingiz, keyin esa fmt-ni argument sifatida qabul qilib, sizning xaritalash vektoringizdir. Agar noto'g'ri bo'lsam, iltimos meni to'g'rilab qo'ying. Aytgancha, menda ma'lumotlar o'qigan joydan fayl bor. demo.txt ko'rsatilgandek yangi oyna yaratish zarurati bormi? Boshim ustidan g'alaba qozonadigan narsalar.
qo'shib qo'ydi muallif Prishu, manba

Tasavvur qiling:

(def data
  "1|Austin|Germany|34-554567
   2|Mary Jane|Australia|45-78647
   3|King Kong|New-Zealand|35-467533")

(->> (for [line (clojure.string/split data #"[ ]*[\r\n]+[ ]*")]
       (-> line (clojure.string/split #"\|") rest vec))
     (map vector (rest (range))))

; ([1 ["Austin" "Germany" "34-554567"]]
;  [2 ["Mary Jane" "Australia" "45-78647"]]
;  [3 ["King Kong" "New-Zealand" "35-467533"]])

Natijada siz nima uchun aniq avtomatik yaratilgan identifikatorga ega bo'lishni xohlaysiz va asl ma'lumotlarga ega bo'lgan ketma-ket raqamni e'tiborsiz qoldirishni istamasangiz ham.

Majburiy qiymatlarni qiymatlari bilan eşleştiğinizde ixtiyoriy ravishda (tartibida-xarita) qo'shing va bu hash xaritasidan farqli o'laroq id tartibini saqlab qoladi.

0
qo'shib qo'ydi
Fayl mazmunini mag'lubiyatga aylantirish uchun slurp dan foydalanishingiz mumkin, hech bo'lmasa mutlaq fayl yo'lini ishlatsangiz. Siz tasvirlagan "chiqish" Clojure ma'lumotlar tuzilmasi emas, shuning uchun uni Clojure funktsiyasi tomonidan ishlab chiqarish mumkin emas. Buning o'rniga bosib chiqarishni xohlaysizmi? Ehtimol ni ga sorted-map ga qo'shishni xohlaysizmi?
qo'shib qo'ydi muallif NikoNyrh, manba
nth va get kabi bir vektor elementini olish uchun bir necha funksiya mavjud. Ular shuningdek, "funktsiyalar" sifatida faoliyat yuritishi mumkin, masalan, (["Austin" "Germaniya" "34-554567"] 1) "Germany" ga qarab baholanadi.
qo'shib qo'ydi muallif NikoNyrh, manba
Salom @NikoNyrh, iltimos, men bilan javobingizni yangilashingiz mumkin, chunki men matnli fayllardan ma'lumotlarni olishda va ko'rsatilgan amaliyotni qo'llashda ozgina muammoga duch kelmoqdaman.
qo'shib qo'ydi muallif Prishu, manba
(1) [1] [1] natijasini berish kabi [1] ["Ostin" "Germaniya" "34-554567"]] qiymatini qanday qilib olsam bo'ladi? va boshqalar.
qo'shib qo'ydi muallif Prishu, manba

balki

(into {}  (map-indexed
       #(vector (inc %1) (rest %2))
       (repeat 2 ["1" "Austin" "Germany" "34-554567"])))
0
qo'shib qo'ydi

balki

(into {}  (map-indexed
       #(vector (inc %1) (rest %2))
       (repeat 2 ["1" "Austin" "Germany" "34-554567"])))
0
qo'shib qo'ydi