I've hopefully got a pretty easy one for you all! I need to append several rows to a csv. Here's the general structure:
f=((np.array(i)).tolist())
g=((np.array(j)).tolist())
h=((np.array(k)).tolist())
with open('output.csv','a') as z:
z.write(",".join(map(str,f)))
This is great for a single row of data! However, I have several rows to add. If I try doing this, all of the data is appended as one row!
f=((np.array(i)).tolist())
g=((np.array(j)).tolist())
h=((np.array(k)).tolist())
with open('output.csv','a') as f:
z.write(",".join(map(str,f)))
z.write(",".join(map(str,g)))
z.write(",".join(map(str,h)))
My question boils down to: how do I append several lists to my csv as separate rows? Can I slap a \n somewhere?
You shouldn't be trying to roll your own CSV writer. You should use the csv module's CSVWriter object:
import csv
with open('output.csv', 'w') as store:
writer = csv.writer(store)
for row in [i, j, k]:
writer.writerow((np.array(row)).tolist())
Related
I want to create a program in which reads a CSV file and writes in another file. My problem is, the file I'm ready is kinda big and I don't want to go through every column by doing this:
columns = defaultdict(list)
reader = csv.DictReader(csvfile)
for row in reader:
for (k,v) in row.items():
columns[k].append(v)
print(columns['name'])
print(columns['id'])
...
I wanted to, instead, do columns[0] to find 'name', and so on. Is there any way I can do this?
You are now reading the CSV with a DictReader this creates the columns based on names, in your case you could just use the reader:
columns = defaultdict(list)
reader = csv.reader(csvfile)
next(reader) # to skip the header row
for row in reader:
for i, v in enumerate(row):
columns[i].append(v)
print(columns[0])
print(columns[1])
I'm not sure that I understand your question. If you are asking, "can I read only the first column?", then the short answer is no. CSV is specifically designed to read a fixed number of columns from variable length records. More specifically, the data is organized as a list of rows, not a list of columns. You can't just seek past what you don't want to read. It sounds like what you are trying to do is reorganized your data into columns.
If you want to minimize the processing of what you do read, it sounds like all you need to do is use csv.reader and skip the first row containing the header. Each row from the reader will return a list of strings and the construction of this list should be less expensive than a map.
If you collect the list of rows you can then put it in a numpy array. A numpy array will allow you to access columns (e.g., x[:, 0]) or rows (e.g., x[0, :]).
Given that I am not entirely sure what you are asking, my answers may not not be what you are looking for; however, whatever your problem is, I am certain you cannot avoid reading the entire file.
I have an array named genrelist that contains all the different genres of a movie. How do i write them out to the csv such that each element in the genrelist is in one cell and they are in a row instead of a column in Python 3.6?
Currently, i can write them out in a column by using this code:
with open('data.csv', 'a') as csvFile:
csvFileWriter = csv.writer(csvFile)
for genre in genrelist:
csvFileWriter.writerow([genre])
csvFile.close()
This will produce an output of:
|shonen|
|action|
|Adventure|
Desired output: |shonen| |action| |adventure|
The for loop writes the single genre to a row, like you desire, but you initiate a new row every single time! This makes the multiple rows seem like a column. Your desired output can be generated by printing the entire genreList with the writerow function. Like so:
with open('data.csv', 'a') as csvFile:
csvFileWriter = csv.writer(csvFile)
csvFileWriter.writerow(genreList)
csvFile.close()
The module pandas happens to have a really nice read_csv() function and also a df.to_csv function.
What you would do is create a dataframe like so:
import pandas as pd
df = pd.DataFrame(read_csv('data.csv'))
to change the columns to rows, just use:
df.transpose()
and then you can write it to a file like this:
df.to_csv('transposeddata.csv')
The full documentation can be found here:
Pandas Documentation
Started learning python after lots of ruby experience. With that context in mind:
I have a csv file that looks something like this:
city_names.csv
"abidjan","addis_ababa","adelaide","ahmedabad"
With the following python script I'd like to read this into a list:
city_names_reader.py
import csv
city_name_file = r"./city_names.csv"
with open(city_name_file, 'rb') as file:
reader = csv.reader(file)
city_name_list = list(reader)
print city_name_list
The result surprised me:
[['abidjan', 'addis_ababa', 'adelaide', 'ahmedabad']]
Any idea why I'm getting a nested list rather than a 4-element list? I must be overlooking something self-evident.
A CSV file represents a table of data. A table contains both columns and rows, like a spreadsheet. Each line in a CSV file is one row in the table. One row contains multiple columns, separated by ,
When you read a CSV file you get a list of rows. Each row is a list of columns.
If your file have only one row you can easily just read that row from the list:
city_name_list = city_name_list[0]
Usually each column represent some kind of data (think "column of email addresses"). Each row then represent a different object (think "one object per row, each row can have one email address"). You add more objects to the table by adding more rows.
It is not common with wide tables. Wide tables are those that grow by adding more columns instead of rows. In your case you have only one kind of data: city names. So you should have one column ("name"), with one row per city. To get city names from your file you could then read the first element from each row:
city_name_list = [row[0] for row in city_name_list]
In both cases you can flatten the list by using itertools.chain:
city_name_list = itertools.chain(city_name_list)
As others suggest, your file is not an idiomatic CSV file. You can simply do:
with open(city_name_file, "rb") as fp:
city_names_list = fp.read().split(",")
Based on comments, here is a possible solution:
import csv
city_name_file = r"./city_names.csv"
city_name_list = []
with open(city_name_file, 'rb') as file:
reader = csv.reader(file)
for item in reader:
city_name_list += item
print city_name_list
Based on a given SQL-Statement, I extract from a database to CSV with thefollowing function:
def extract_from_db():
with open('myfile.csv','w') as outfile:
for row in cursor:
outfile.write(str(row[0])+";"+str(row[1])+";"+str(row[2])+";"+str(row[3])+";"+str(row[4])+";"+str(row[5])
+";"+str(row[6])+";"+str(row[7])+";"+str(row[8])+";"+str(row[9])+";"+str(row[10])+";"+str(row[11])+";"+str(row[12])
+";"+str(row[13])+";"+str(row[14])+"\n")
How can I write in the beginning of the file the column names for a variable amount of columns, so that I don't have to hardcode it? Also the hardcoded concatenation is pretty ugly.
You could use the description
desc = cursor.description
function. It returns a sequence of 7 item sequences and you can get the column names from
for seq in desc:
print seq[0]
I would also recommend using pandas to do your writing to csv.
Ebrahim Jackoet has already mentioned that you can use cursor.description to get the column names from your query. If you don't have a very large number of rows to process, though, the csv module is built in and makes writing rows simple. It also handles all of the necessary quoting
An example follows:
import csv
with open("myfile.csv", "w") as outfile:
writer = csv.writer(outfile, delimiter = ";")
for row in cursor:
writer.writerow(row)
Python 2.6(necessary for the job)
import csv
list = ['apple,whiskey,turtle', 'orange,gin,wolf', 'banana,vodka,sparrow']
fieldNames = ['Fruit', 'Spirit', 'Animal']
reader = csv.DictReader(list,fieldnames= fieldNames)
for row in reader:
print row['Fruit']
for row in reader:
print row['Fruit']
I have some code that generates a uniform list of items per row, making a list object. For ease of use I used the csv module's DictReader to step through the rows and do any calculations I need to but when I try to iterate a second time, I get no output. I suspect the end of the list is being treated like an EOF but I am unable to 'seek' to the beginning of the list to do the iteration again.
Any suggestions on what I can do? Perhaps there is a better way than using the CSV, it just seemed really convenient.
New Code
import csv
list = ['apple,"whiskey,rum",turtle', 'orange,gin,wolf', 'banana,vodka,sparrow']
processed = []
fieldNames = ['Fruit', 'Spirit', 'Animal']
reader = csv.DictReader(list,fieldnames= fieldNames, quoatechar = '"')
for row in reader:
processed.append(row)
print row
for row in processed:
print row['Fruit']
for row in processed:
print row['Spirit']
#jonrsharpe suggested placing the rows of reader into a list. It works perfectly for what I had in mind. Thank you everyone.
You're indeed correct that iterating over the rows once is what the DictReader provides. So your options are:
Create a new DictReader and iterate again (seems wasteful)
Iterate over the rows once and perform all computations that you want to perform
Iterate over the rows once, store the data in another data structure and iterate over that data structure as many times as you wish.
Also, if you have only the list and the field names you don't need a DictReader to do the same thing. If you know the data is relatively straightforward (no comma's inside the data for example and all the same number of items) then you can simply do:
merged = [zip(fieldnames, row.split(",")) for row in my_list]
print merged