Python: Write two lists into two column text file - list

Say I have two lists:
a=[1,2,3]
b=[4,5,6]
I want to write them into a text file such that I obtain a two column text file:
1 4
2 5
3 6

Simply zip the list, and write them to a csv file with tab as the delimiter:
>>> a=[1,2,3]
>>> b=[4,5,6]
>>> zip(a,b)
[(1, 4), (2, 5), (3, 6)]
>>> import csv
>>> with open('text.csv', 'w') as f:
... writer = csv.writer(f, delimiter='\t')
... writer.writerows(zip(a,b))
...
>>> quit()
$ cat text.csv
1 4
2 5
3 6

You can use numpy.savetxt(), which is a convenient tool from the numpy library.
A minimal example would be as follows:
import numpy as np
xarray = np.array([0, 1, 2, 3, 4, 5])
yarray = np.array([0, 10, 20, 30, 40, 50])
# here is your data, in two numpy arrays
data = np.column_stack([xarray, yarray])
datafile_path = "/your/data/output/directory/datafile.txt"
np.savetxt(datafile_path , data, fmt=['%d','%d'])
# here the ascii file is written.
The fmt field in np.savetxt() in the example specifies that the numbers are integers.
You can use a different format for each column.
E.g. to specify floating point format, with 2 decimal digits and 10 characters wide columns, you would use '%10.2f'.

Try this:
file = open("list.txt", "w")
for index in range(len(a)):
file.write(str(a[index]) + " " + str(b[index]) + "\n")
file.close()

A simple solution is to write columns of fixed-width text:
a=[1,2,3]
b=[4,5,6]
col_format = "{:<5}" * 2 + "\n" # 2 left-justfied columns with 5 character width
with open("foo.csv", 'w') as of:
for x in zip(a, b):
of.write(col_format.format(*x))
Then cat foo.csv produces:
1 4
2 5
3 6
The output is both human and machine readable, whereas tabs can generate messy looking output if the precision of the values varies along the column. It also avoids loading the separate csv and numpy libraries, but works with both lists and arrays.

You can write two lists into a text file that contains two columns.
a=[1,2,3]
b=[4,5,6]
c = [a, b]
with open("list1.txt", "w") as file:
for x in zip(*c):
file.write("{0}\t{1}\n".format(*x))
Output in the text file:
1 4
2 5
3 6

It exits a straightway to save and stack same vectors length in columns. To do so use the concatenate function, you can then stack 3,4 or N vectors in columns delimitered by a tab.
np.savetxt('experimental_data_%s_%.1fa_%dp.txt'%(signal,angle,p_range), np.c_[DCS_exp, p_exp], delimiter="\t")

Related

Loading numerical data from a text file in python

I have a text file which is
1.25e5 15
2.7e6 12
18.e5 14
I want to read the text as a 2d array and assign the first column as x and second as y.
Can anyone help me how can I do that. I did
f = open('energy.txt', 'r')
x = f.readlines()
but I don't know how to create the first column.
Since you're okay with numpy, you can just use np.loadtxt:
In [270]: np.loadtxt('energy.txt')
Out[270]:
array([[ 1.25000000e+05, 1.50000000e+01],
[ 2.70000000e+06, 1.20000000e+01],
[ 1.80000000e+06, 1.40000000e+01]])
Alternatively, the python way to do this is:
In [277]: data = []
In [278]: with open('energy.txt') as f:
...: for line in f:
...: i, j = line.split()
...: data.append([float(i), int(j)])
...:
In [279]: data
Out[279]: [[125000.0, 15], [2700000.0, 12], [1800000.0, 14]]
With this approach, you store data as a list of lists, not a numpy array of floats. Also, you'll need to add a try-except in case you have any deviant lines in your file.

Selecting only one row at a time for iteration in PANDAS-PYTHON

I have this following code and a text file with 5 (X and Y) values The Image of the text file is here. I need to iterate 1000 times for every X and Y value. How can I achieve this?
import pandas as pd
data = pd.read_csv("test.txt", delim_whitespace=True, skipinitialspace=True,)
for every line in the text document:
for i in range(1, 1001, 1):
z = data["X"] + data["Y"]
z = z + 10
print z
The text file is like
X Y
1 10
2 20
3 30
4 40
5 50
The output must be:
10011
10022
10033
10044
10055
You can select one row at the time using .loc. Please read this documentation to fully understand how this work. Here is your data:
import pandas as pd
df = pd.DataFrame({'X':['1','2','3','4','5'], 'Y': ['10','20','30','40','50']})
This code
print df.loc[0]
will give you the first row (with index=0) as a pandas series (pd.Series), which is essentially like a dataframe with one column only: a vector.
X 1
Y 10
Name: 0, dtype: object
If you want the second row then: df.loc[1] and so on...
If you want to iterate one row at the time, you can select each row in the first for loop and perform your operations 1000 times in the second for loop:
for ix in df.index: # df.index gives [0,1,2,3,4]
for i in xrange(0,1000):
ser = df.loc[ix]
print ser['X'] + ser['Y'] + '10'
Try this,
data = pd.DataFrame({'X': [1, 2, 3, 4, 5], 'Y': [10,20,30,40,50]})
for each_line in data.index:
z = data['X'].loc[each_line] + data['Y'].loc[each_line]
for i in range(1,1001,1):
z +=10
print(z)
Output
10011
10022
10033
10044
10055
if you want to add new column to dataFrame:
data["total"] = sorted(set([(data.loc[ix]['X'].astype(int) + data.loc[ix]['Y'].astype(int)).astype(str) +"10" for ix in data.index for i in range(1,1001)]))
if you want concatenate the 'X' and 'Y' +'10' then:
[data.loc[ix]['X'].astype(str) + data.loc[ix]['Y'].astype(str) +"10" for ix in data.index for i in range(1,1001)]
And if you want to sum of 'X' + 'Y' and concat + '10' then:
final_data = [(data.loc[ix]['X'].astype(int) + data.loc[ix]['Y'].astype(int)).astype(str) +"10" for ix in data.index for i in range(1,1001)]

How can I print output with a defined number of characters in each line with python?

I used textwrap.fill (textwrap.fill(text, 6)) to limit each line in only 6 characters, but there is a problem with using this command because my purpose is go to new line exact at 6 character, I mean:
for example using textwrap.fill(I am a student, 8):
what I want:
(I am a s
tudent)
output:
(I am a
student)
One approach:
>>> text = 'I am a student, 8'
>>> text = 'I am a student'
>>> for i in range(0, len(text), 8):
... print text[i:i+8]
...
I am a s
tudent
for i in range(0, len(text), 8) means "Give me numbers starting at 0, incrementing by 8 at a time, and ending before the length of the text."
EDIT
If you want the value in a single string:
>>> wrapped = "\n".join(text[i:i+8] for i in range(0, len(text), 8))
>>> wrapped
'I am a s\ntudent'

write the same data into many lines in text file python

I would like to write the same information for many lines into a text file. Basicly, I have a list of numbers. I want to write these number in one line and then copy the first line to the next 400 lines.
My code at the moment is
outfile = open(outfilename+'.dat','w')
for j in range (0,len(elevation_list)):
outfile.write(elevation_list[j]+' ')
outfile.close()
And it only writes the first line.
For example, my elevation list is 1, 2, 3, 4, 5
I want my text file like the following
1 2 3 4 5
1 2 3 4 5
1 2 3 4 5
Can anyone please help me with this?
Do you have any line breaks in your elevation list? Try this instead:
elevations = ""
for elevation in elevation_list:
elevations+= elevation
outfile = open(outfilename+'.dat','w')
for i in range(400):
outfile.write(elevations +'\n')
outfile.close()
This is what you want:
class RepeatedWrite(object):
def __init__(self, elevation_list, no_of_lines=5, outfilename="outfile.dat"):
self.elevation_list = elevation_list
self.no_of_lines = no_of_lines
self.outfilename = outfilename
def write_to_file(self):
with open(self.outfilename, 'w') as fp:
for i in xrange(self.no_of_lines):
fp.write(' '.join([str(ele) for ele in self.elevation_list]))
fp.write("\n")
elevation_list = [1, 2, 3, 4, 5]
RepeatedWrite(elevation_list).write_to_file()

Taking an input as multiple elements instead of only 1

I'm trying to create a function that will take the input of the user to create a 3x4 matrix, then find the sum of each column individually. But I'm not sure how to set up the input so that I'll be given each number individually instead of a long string.
def testMatrixFunctions():
row0 = input("Enter a 3-by-4 matrix row for row 0: ")
row1 = input("Enter a 3-by-4 matrix row for row 1: ")
row2 = input("Enter a 3-by-4 matrix row for row 2: ")
I could also use some help with adding the columns, but my biggest concern is the input at the moment.
Use the str.split() method:
>>> "1 2 3 4 5".split()
['1', '2', '3', '4', '5']
And then convert each string into an integer:
>>> map(int, "1 2 3 4 5".split())
[1, 2, 3, 4, 5]
>>> [int(c) for c in "1 2 3 4 5".split()]
[1, 2, 3, 4, 5]
Use split() function, which will split the input and you can 'eval' each element.
[eval(eachItem) for eachItem in inputList]
That will accept input regardless of the datatype.