Best way to access the Nth line of csv file

后端 未结 6 1207
陌清茗
陌清茗 2020-12-13 13:56

I have to access the Nth line in a CSV file.

Here\'s what I did:

import csv

the_file = open(\'path\', \'r\')
reader = csv.reader(the_file)

N = inpu         


        
相关标签:
6条回答
  • 2020-12-13 14:00

    You could minimize your for loop into a comprehension expression, e.g.

    row = [row for i,row in enumerate(reader) if i == N][0]  
    
    # or even nicer as seen in iCodez code with next and generator expression
    
    row = next(row for i,row in enumerate(reader) if i == N)
    
    0 讨论(0)
  • 2020-12-13 14:04

    Your solution is actually not that bad. Advancing the file iterator to the line you want is a good approach and is used in many situations like this.

    If you want it more concise though, you can use next and enumerate with a generator expression:

    import csv
    
    the_file = open('path', 'r')
    reader = csv.reader(the_file)
    
    N = int(input('What line do you need? > '))
    
    line = next((x for i, x in enumerate(reader) if i == N), None)
    print(line)
    
    the_file.close()
    

    The None in there is what will be returned if the line is not found (N is too large). You can pick any other value though.


    You could also open the file with a with-statement to have it be automatically closed:

    import csv
    
    with open('path', 'r') as the_file:
        reader = csv.reader(the_file)
    
        N = int(input('What line do you need? > '))
    
        line = next((x for i, x in enumerate(reader) if i == N), None)
        print(line)
    

    If you really want to cut down on size, you could do:

    from csv import reader
    N = int(input('What line do you need? > '))
    with open('path') as f:
        print(next((x for i, x in enumerate(reader(f)) if i == N), None))
    
    0 讨论(0)
  • 2020-12-13 14:04
    import csv
    with open('cvs_file.csv', 'r') as inFile: 
        reader = csv.reader(inFile)
        my_content = list(reader)
    
    line_no = input('What line do you need(line number begins from 0)? > ')
    if line_no < len(my_content):
        print(my_content[line_no])
    else:
        print('This line does not exists')
    

    As a result now you can get any line by its index directly:

    What line do you need? > 2
    ['101', '0.19', '1']
    
    What line do you need? > 100
    This line does not exists
    
    0 讨论(0)
  • 2020-12-13 14:11

    It makes little difference but it is slightly cleaner to use enumerate rather than making your own counter variable.

    for i, row in enumerate(reader):
        if i == N:
            print("This is the line.")
            print(row)
            break
    

    You can also use itertools.islice which is designed for this type of scenario - accessing a particular slice of an iterable without reading the whole thing into memory. It should be a bit more efficient than looping through the unwanted rows.

    with open(path, 'r') as f:
        N = int(input('What line do you need? > '))
        print("This is the line.")
        print(next(itertools.islice(csv.reader(f), N, None)))
    

    But if your CSV file is small, just read the entire thing into a list, which you can then access with an index in the normal way. This also has the advantage that you can access several different rows in random order without having to reset the csv reader.

    my_csv_data = list(reader)
    print(my_csv_data[N])
    
    0 讨论(0)
  • 2020-12-13 14:16

    The itertools module has a number of functions for creating specialized iterators — and its islice() function could be used to easily solve this problem:

    import csv
    import itertools
    
    N = 5  # desired line number
    
    with open('path.csv', newline='') as the_file:
        row = next(csv.reader(itertools.islice(the_file, N, N+1)))
    
    print("This is the line.")
    print(row)
    

    P.S. For the curious, my initial response — which also works (arguably better) — was:

        row = next(itertools.islice(csv.reader(the_file), N, N+1))
    
    0 讨论(0)
  • 2020-12-13 14:20

    You can simply do:

    n = 2 # line to print
    fd = open('foo.csv', 'r')
    lines = fd.readlines()
    print lines[n-1] # prints 2nd line
    fd.close()
    

    Or even better to utilize less memory by not loading entire file into memory:

    import linecache
    n = 2
    linecache.getline('foo.csv', n)
    
    0 讨论(0)
提交回复
热议问题