นับจำนวนฟิลด์ในแต่ละระเบียน csv


12

ลองนึกภาพไฟล์ข้อความที่แต่ละระเบียน csv อาจมีจำนวนฟิลด์ต่างกัน ภารกิจคือการเขียนโค้ดเพื่อแสดงจำนวนฟิลด์ที่มีในแต่ละเรคคอร์ดของไฟล์ คุณสามารถสมมติว่าไม่มีบรรทัดส่วนหัวในไฟล์และสามารถอ่านได้จากไฟล์หรืออินพุตมาตรฐานตามที่คุณเลือก

คุณสามารถสมมติรุ่นของrfc4180สำหรับกฎ csv ซึ่งฉันจะอธิบายด้านล่างสำหรับคำจำกัดความของแต่ละบรรทัดของไฟล์ นี่เป็นเวอร์ชั่นที่แก้ไขเล็กน้อยของส่วนที่เกี่ยวข้องของข้อมูลจำเพาะ:

คำจำกัดความของรูปแบบ CSV

  1. แต่ละระเบียนจะอยู่ในบรรทัดที่แยกต่างหากคั่นด้วยตัวแบ่งบรรทัด (CRLF) ตัวอย่างเช่น:

    aaa,bbb,ccc CRLF
    zzz,yyy,xxx CRLF

  2. ระเบียนสุดท้ายในไฟล์อาจมีหรือไม่มีตัวแบ่งบรรทัดสิ้นสุด ตัวอย่างเช่น:

    aaa,bbb,ccc CRLF
    zzz,yyy,xxx

(กฎข้อ 3. ใช้ไม่ได้กับการท้าทายนี้)

  1. ภายในแต่ละระเบียนอาจมีหนึ่งหรือมากกว่าหนึ่งช่องคั่นด้วยเครื่องหมายจุลภาค ช่องว่างถือเป็นส่วนหนึ่งของเขตข้อมูลและไม่ควรละเว้น

  2. แต่ละฟิลด์อาจมีหรือไม่มีก็ได้ในเครื่องหมายคำพูดคู่ หากเขตข้อมูลไม่ได้อยู่ในเครื่องหมายคำพูดคู่การอ้างอิงสองครั้งอาจไม่ปรากฏในเขตข้อมูล ตัวอย่างเช่น:

    "aaa","bbb","ccc" CRLF
    zzz,yyy,xxx

  3. ฟิลด์ที่มีตัวแบ่งบรรทัด (CRLF) เครื่องหมายคำพูดคู่และเครื่องหมายจุลภาคควรอยู่ในเครื่องหมายคำพูดคู่ ตัวอย่างเช่น:

    "aaa","b CRLF
    bb","ccc" CRLF
    zzz,yyy,xxx

  4. หากมีการใช้เครื่องหมายอัญประกาศคู่เพื่อใส่เขตข้อมูลดังนั้นเครื่องหมายอัญประกาศคู่ที่ปรากฏภายในเขตข้อมูลจะต้องถูกหลีกเลี่ยงโดยนำหน้าด้วยเครื่องหมายคำพูดคู่อื่น ตัวอย่างเช่น:

    "aaa","b""bb","ccc"

ตัวอย่าง

การป้อนข้อมูล:

,"Hello, World!"
"aaa","b""bb","ccc"
zzz,yyy,
"aaa","b 
bb","ccc","fish",""

ควรให้ผลลัพธ์:

2, 3, 3, 5

คุณสามารถให้ค่าผลลัพธ์ในวิธีที่คุณสะดวกที่สุด

ห้องสมุด

คุณสามารถใช้ห้องสมุดใดก็ได้ที่คุณชอบ


คำตอบที่ดีเลิศ แต่เรายังขาดบรรทัดคำสั่ง / คำตอบ bash ซึ่งจะยอดเยี่ยมโดยเฉพาะ

คำตอบ:


5

Stax , 19 12 ไบต์

èJ§3‼}vAà○L>

เรียกใช้และแก้ไขข้อบกพร่อง

คลายกล่อง ungolfed และแสดงความคิดเห็นมันมีลักษณะเช่นนี้

_'"/    split *all* of standard input by double quote characters
2::     keep only the even numbered elements
|j      split on newlines (implicitly concatenates array of "strings")
m       for each line, execute the rest of the program and output
  ',#^  count the number of commas occurring as substrings, and increment

เรียกใช้อันนี้


1
มันทำงานยังไง?
Anush

1
@Anush: ฉันได้เพิ่มข้อมูลเพิ่มเติม
เรียกซ้ำ


3

JavaScript (ES2018), 42 59 ไบต์

s=>s.replace(/".+?"/sg).split`\n`.map(c=>c.split`,`.length)


ในทางเทคนิคนี่คือ ES2018 เนื่องจากการsตั้งค่าสถานะใน regex ไม่ใช่ว่ามันสำคัญมาก ;-) และใช้ประโยชน์ได้ดี btw!
ETHproductions

2
ฟังก์ชั่นนี้ใช้งานได้ครั้งละหนึ่งระเบียนเท่านั้น ฉันคิดว่าคำอธิบายปัญหาต้องการการจัดการไฟล์หลาย ๆ ไฟล์ทั้งชุด
เรียกซ้ำ

@ ETHproductions จุดดีจะอัปเดต
Rick Hitchcock

@ recursive คุณพูดถูกฉันเข้าใจผิดอินพุต อัปเดตทันทีที่สูญเสียจำนวนมากหลายไบต์
Rick Hitchcock

3

เยลลี่ 12 ไบต์

ṣ”"m2FỴ=”,§‘

พอร์ตของคำตอบ Stax แบบเรียกซ้ำ - ไปให้เครดิต!

ลองออนไลน์!

อย่างไร?

ṣ”"m2FỴ=”,§‘ - Link: list of characters, V
 ”"          - a double quote character = '"'
ṣ            - split (V) at ('"')
   m2        - modulo slice with two (1st, 3rd, 5th, ... elements of that)
     F       - flatten list of lists to a list
      Ỵ      - split at newlines
        ”,   - comma character = ','
       =     - equal? (vectorises)
          §  - sum each
           ‘ - increment (vectorises)
             - (as a full program implicit print)

บางทีคุณอาจต้องการṣ”"m2ẎỴċ€”,‘- กระชับและċ€นับจุลภาคในแต่ละ


2

Python ขนาด 63 ไบต์

import csv
def f(s):return map(len,csv.reader(s.split("\n"))

ส่งคืนผลลัพธ์ในmapวัตถุiterable


2
การใช้lambdaฟังก์ชั่นนี้คุณสามารถลดขนาดได้ถึง54 ไบต์
ovs

@ovs ฉันอาจไม่เข้าใจกฎ แต่ TIO ของคุณดูเหมือนจะป้อนข้อมูลล่วงหน้า ถูกต้องจริงเหรอ?
Anush

ฉันเห็นว่าทำไมมันใช้งานได้ในขณะนี้ (ขอบคุณ @ ASCII- เท่านั้น)
Anush



2

Java 10, 101 ไบต์

s->{for(var p:s.replaceAll("\"[^\"]*\"","x").split("\n"))System.out.println(p.split(",",-1).length);}

ลองออนไลน์

คำอธิบาย:

s->{                                    // Method with String parameter and no return-type
  for(var p:s.replaceAll("\"[^\"]*\"","x") 
                                        //  Replace all words within quotes with an "x"
             .split("\n"))              //  Then split by new-line and loop over them:
    System.out.println(p.split(",",-1)  //   Split the item by comma's
                        .length);}      //   And print the length of this array

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.