1

I have some text files that I want to read file by file and line by line and sort and write to one file in Python, for example:

file 1:
C
D
E

file 2:
1
2
3
4

file 3:
#
$
*

File 4,.......

The result should be like this sequence in one file:

C
1
#
D
2
$
E
3
*
C
4
#
D
1
#
  • Welcome to Stack Overflow! Please [edit] your question to show [what you have tried so far](http://whathaveyoutried.com). You should include a [mcve] of the code that you are having problems with, then we can try to help with the specific problem. You should also read [ask]. – Toby Speight Nov 01 '16 at 08:41
  • What is the logic of sorting the 4 files, even a pseudo code. – M.Hassan Nov 01 '16 at 08:50

2 Answers2

1

You can use a list of iterators over your files. You then need to constantly cycle through these iterators until one of your files has been consumed. You could use a while loop, or shown here is using itertools cycle:

import glob
import itertools

fs = glob.glob("./*py")  # Use glob module to get files with a pattern

fits = [open(i, "r") for i in fs]  # Create a list of file iterators

with open("blah", "w") as out:
    for f in itertools.cycle(fits):  # Loop over you list until one file is consumed
        try:
            l = next(f).split(" ")
            s = sorted(l)
            out.write(" ".join(s) + "/n")
            print s
        except:  # If one file has been read, the next(f) will raise an exception and this will stop the loop
            break
kezzos
  • 3,023
  • 3
  • 20
  • 37
  • it doesn't work- even did't write any line to new file! also just please check my results, there are after read first line of file should be read second line of second file ,... – Danial Gotze Nov 01 '16 at 10:42
  • Comment out the try and except lines and then see what the error message is. this should help you – kezzos Nov 01 '16 at 10:53
  • TypeError: write() argument must be str, not list ['1\n'] – Danial Gotze Nov 01 '16 at 11:00
  • Use " ".join(s) – kezzos Nov 01 '16 at 11:05
  • thanks for answer but the result is not correct, I have result like C 1 # D 2 $ E3 * – Danial Gotze Nov 01 '16 at 11:23
  • You need an end of line character "/n" – kezzos Nov 01 '16 at 11:25
  • Thanks a lot, But still not correct result , after (E 3 *) should be again write string because second file is not finished! So, after (E 3 * ) I have to write (C 4 # D 1 #) , because as explained second file is not ended and should be repeat again, please look again my results in my question post. really thanks for helping . – Danial Gotze Nov 01 '16 at 11:39
0

This looks related to another question you asked (and then deleted).

I'm assuming you want to be able to read a file, create generators, combine generators, sort the output of generators, then write to a file.

Using yield to form your generator makes life a lot easier.

Keep in mind, to sort every line like this, you will have to store it in memory. If dealing with very large files, you will need to handle this in a more memory-conscious way.

First, let's make your generator that opens a file and reads line-by-line:

def line_gen(file_name):
    with open(file_name, 'r') as f:
        for line in f.readlines():
            yield line

Then let's "merge" the generators, by creating a generator which will iterate through each one in order.

def merge_gens(*gens):
    for gen in gens:
        for x in gen:
            yield x

Then we can create our generators:

gen1 = line_gen('f1.txt')
gen2 = line_gen('f2.txt')

Combine them:

comb_gen = merge_gens(gen1, gen2)

Create a list from the generator. (This is the potentially-memory-intensive step.):

itered_list = [x for x in comb_gen]

Sort the list:

sorted_list = sorted(itered_list)

Write to the file:

with open('f3.txt', 'w') as f:
    for line in sorted_list:
        f.write(line + '\n')
Community
  • 1
  • 1
Paul
  • 3,634
  • 1
  • 18
  • 23