I have this code, that would prompt the user for an .mtx file (e.g. Mydata.mtx) that contain a matrix of integers. the program would take this matrix, transpose it, then create a new file with the transposed matrix.
the file is a simple .mtx file.
the original file (Mydata.mtx):
1 2 3 4 5
6 7 8 9 10
11 12 13 14 15 #separated by a tap "\t" to be a matrix
here is the code:
def readMatrix(filename):
listOfLists = []
file = open(filename)
for i in file:
listOfLists.append(i.split())
return listOfLists
def transpose(M):
mtranspose = [list(i) for i in zip(*M)]
return mtranspose
def writeMatrix(M, filename):
for i in M:
convertListToStr = str(i)
newFile = open("T_" + filename, "w")
newFile.write(convertListToStr)
newFile.close()
callFile = input("Enter the file name: ")
toReadFile = readMatrix(callFile)
toTranspose = transpose(toReadFile)
ToWriteMatrix = writeMatrix(toTranspose, callFile)
the code functions, in that it transposes the matrix and creates a new file. so the problems is in the third function writeMatrix in for i in M as it does not print out the whole matrix but only last line in list form. I need it in a string form.
my output (in the new file):
T_Mydata.mtx
['5', '10', '15']
desired output:
1 6 11
2 7 12
3 8 13
4 9 14
5 10 15
can anyone help?
You need to write each row in the matrix as you loop over them, you also need to join each element in the row instead of converting the entire row to a string
def writeMatrix(M, filename):
with open("T_" + filename, "w") as f:
for row in M:
f.write(" ".join(row) + "\n")
Related
I am fairly new to python. I have been trying to write nested lists which contain several lists which are in the form of x,y,z coordinates to a file one row at a time.
Ex: lists I have are like this
x = [[1,2,3],[4,5,6],[7,8,9]]
y = [[10,11,12],[13,14,15],[16,17,18]]
what I want to write them is like this:
Say I have a file called ring1.xyz.
If you open it, it should be like.
H 1 2 3
H 4 5 6
H 10 11 12
H 13 14 15
Only the first two lists should be written to the file.
I currently tried this code block, but it is not working.
any lead\solution is appreciated
for s in range(3):
with open("ring_%s.xyz" %s, "w+") as f:
for k in range(2):
for j in x[k]:
f.write('H\n')
f.write(' ')
f.write('%s' % j)
You can try this:
def open_file(l,ind):
with open("ring"+ind+".txt","a+") as f:
for i in l[:2]:
f.write("H "+" ".join(i))
f.write("\n")
x = [[1,2,3],[4,5,6],[7,8,9]]
y = [[10,11,12],[13,14,15],[16,17,18]]
open_file(x,1)
open_file(y,2)
Try this code and tell me if it helped:-
for s in range(3):
with open("ring"+s+".xyz") as f:
for i in range(2):
f.write("H ")
for j in x[i]:
f.write(str(j))
f.write(" ")
f.write("\n")
Hi I am very new to programing and coding but I think I am doing pretty good for only a month so far. I have hit a little snag and ran into a problem I do not know how to solve. I have two separate text files that I am taking numbers from and averaging them together and putting the average in a new file. The two text files are zztext.txt & zztext2.txt. There is not the number list like 1), 2), 3), 4), or 5) in the files I did it two show what is on what line number.
This is what is in the zztext.txt:
P3
591 600
255
1 4 3
4 5 6
This is what is in the zztext2.txt:
P3
591 600
255
6 5 4
4 2 6
import os
a = 0
#progarm1-program4 needs name changes
def program1():
print(os.getcwd())
inFile = open('zztext.txt','r')
for i in range(3):
next (inFile)
inFile2 = open('zztext2.txt','r')
for i in range(3):
next (inFile2)
for line in inFile:
first1 = line.split()
print(first1)
print(first1[a])
print('\n')
for line in inFile2:
first2 = line.split()
print(first2)
print(first2[a])
#change [number] to go across
w = int(first1[a]) + int(first2[a])
print(w)
result =
['1', '4', '3'] This returns 1
['4', '5', '6'] This returns 4
['6', '5', '4'] This returns 6
['4', '2', '6'] This returns 4 and the final return is 8 because the 4 and 4 from both lists were added together.
I want the bold 1 and 6 added together and the bold 4 and 5 added together and both put in a new file so it would look like:
P3
591 600
255
7(1 and 6 added) 9(4 and 5 added) and 7(3 and 4 added)
and then the next row of numbers
8(4+4) 7(5+2) 12(6+6)
and so on. Any help would be greatly appreciated! :)
So you are on the right path, just a few small tweaks needed to get you what you want.
def program():
with open("zztext.txt","r") as f1, open("zztext2.txt", "r") as f2:
for _ in range(3):
next(f1)
next(f2)
while True:
try:
l1 = next(f1)
l2 = next(f2)
except StopIteration:
break
xs = map(int, l1.split())
ys = map(int, l2.split())
result = [sum(t) for t in zip(xs, ys)]
print(result)
This prints:
[7, 9, 7]
[8, 7, 12]
I would also suggest breaking your code in to smaller functions. Separate functions that open files, that do the logic, etc..
Welcome to coing and python! Here is the full program, checkout what details you are missing, feel free to ask if you have any questions about my version of the program
def read_file(filename): #returns a list with each line with newline removed
return [line.strip() for line in open(filename, 'r').readlines()]
def all_digits(string): #returns true if all characters are digits in string
return all([char.isdigit() for char in string.split(' ')])
def split_string(string): #returns a list with int of each character in the string
return [int(char) for char in string.split(' ')]
def program(file_1, file_2, outfile):
output = []
for line_file1, line_file2 in zip(read_file(file_1), read_file(file_2)):
if all([not line_file1 == line_file2, all_digits(line_file1), all_digits(line_file2)]):
#if lines don't match and they characters are digits in string
print(f'found digits {line_file1} and {line_file2}, adding their sum to the file..')
new_line = []
for digit1, digit2 in zip(split_string(line_file1), split_string(line_file2)):
new_line.append(str(digit1+digit2))
new_line = ' '.join(new_line)
else:
print(f'adding non-digit line {line_file1} to the file')
new_line = line_file1
output.append(new_line)
output_lines = '\n'.join(output)
open(outfile, "w").write(output_lines)
if __name__ == "__main__":
program("zztext.txt", "zztext2.txt", "output.txt")
You should read about zip and all functions, they are neat
I have a list of proxies separated by line. These proxies need to be separate into separate lists with sizes that I choose.
So I want the program to input how many lists of 10, 25, and 50 I need them to be split into, then output the new lists as a text file. The same proxy cannot be present in two separate lists.
This is what I've got so far simply to count the proxies
filename = input('Enter a file name: ')
with open(filename) as f:
line_count = 0
for line in f:
line_count += 1
print("Number of proxies: " + str(line_count))
Any tips on how to proceed?
You can achieve that by something like that:
def split_list(filename, size)
new_content = []
with open(filename) as f:
content = f.readlines()
for chunk in range(0, len(content), size):
new_content.append(content[chunk:chunk+size])
The code will generate numbers (range) from 0 to the length of the file. Using step param of range, we can increase the starting point by size every iteration.
The code will go through the list, and use slicing to get chunks of elements form the list constructing a new one. Those new lists will be the elements of a new list, new_content.
For a variable sizes try this:
def split_list(filename, sizes):
with open(filename) as f:
content = f.readlines()
new_content = []
start = 0
for size in sizes:
stop = start + size
new_content.append(content[start:stop])
start += size
return new_content
splitted_list = split_list('data.txt', [5, 2, 3])
for i, l in enumerate(splitted_list):
with open('{}.txt'.format(i), 'w') as f:
f.writelines(l)
Given data.txt is
1
2
3
4
5
6
7
8
9
10
it will generate three files (as specified in the second argument of the split_list function):
0.txt with the first 5 lines (the first specified chunk):
1
2
3
4
5
1.txt with the following 2 lines (the second chunk):
6
7
Finally 2.txt with the last 3 lines (third chunk):
8
9
10
I am trying to write each iterated output of for loop for further operations.
Here is my code
#!/usr/bin/python
import io
from operator import itemgetter
with open('test.in') as f:
content = f.readlines()
content = [int(x) for x in content]
content = tuple(content)
nClus = input("Number of Clusters: ")
nEig = input("Number of eigen values: ")
j = 0
k = nClus + 1
content1 = ""
for i in range(1,k):
print content[j*(nEig+1):i*(nEig+1)]
j = j + 1
The file test.in looks like this (which is an example, actual test.in contains huge amount of data)
40
1
4
3
5
7
29
6
9
4
7
3
50
1
2
3
4
5
57
9
8
7
6
5
The values nClus = 4, nEig = 5.
Any suggestions on how to proceed?
Why not just save them to an array (mydata below)? I don't see where j stops (other_dimension, you can probably just delete it if you only have 1 dimension of results, I don't know your array size), but you can follow this format to get a numpy array to save data to:
import numpy as np
... [your code]
mydata = np.zeros([k,other_dimension]) // other_dimension only if you are saving a rectangular matrix of results instead of a vector
for i in range(1,k):
mydata[row, column] = content[j*(nEig+1):i*(nEig+1)] // put your iterators here for row, column if applicable (rectangular matrix), otherwise mydata[iterator]
print mydata[k, other_dimension] // other_dimension only if you are saving a rectangular matrix of results instead of a vector
j = j + 1
i have a .txt file with this(it should be random names, tho):
My Name 4 8 7
Your Name 5 8 7
You U 5 9 7
My My 4 8 5
Y Y 8 7 9
I need to put the information into text file results.txt with the names + average of the numbers. How do I do that?
with open(r'stuff.txt') as f:
mylist = list(f)
i = 0
sk = len(mylist)
while i < sk - 4:
print(mylist[i], mylist[i+1], mylist[i+2], mylist[i+3])
i = i + 3
Firstly, open both the input and output files:
with open("stuff.txt") as in_file:
with open("results.txt", "w") as out_file:
Since the problem only needs to work on each line independently, a simple loop over each line would suffice:
for line in in_file:
Split each line at the whitespaces into list of strings (row):
row = line.split()
The numbers occur after the first two fields:
str_nums = row[2:]
However, these are still strings, so they must be converted to a floating-point number to allow arithmetic to be performed on them. This results in a list of floats (nums):
nums = map(float, str_nums)
Now calculate the average:
avg = sum(nums) / len(str_nums)
Finally, write the names and the average into the output file.
out_file.write("{} {} {}\n".format(row[0], row[1], avg))
what about this?
with open(fname) as f:
new_lines = []
lines = f.readlines()
for each in lines:
col = each.split()
l = len(col)#<-- length of each line
average = (int(col[l-1])+int(col[l-2])+int(col[l-3]))/3
new_lines.append(col[0]+col[1]+str(average) + '\n')
for each in new_lines:#rewriting new lines into file
f.write(each)
f.close()
I tried, and this worked:
inputtxt=open("stuff.txt", "r")
outputtxt=open("output.txt", "w")
output=""""""
for i in inputtxt.readlines():
nums=[]
name=""
for k in i:
try:
nums.append(int(k))
except:
if k!=" ":
name+=k
avrg=0
for j in nums:
avrg+=j
avrg/=len(nums)
line=name+" "+str(avrg)+"\n"
output+=line
outputtxt.write(output)
inputtxt.close()
outputtxt.close()