1

I want to find the first filename myfile????.txt that doesn't exist yet (???? is a number). This works:

import os
i = 0
f = 'myfile%04i.txt' % i
while os.path.exists(f):
    i += 1
    f = 'myfile%04i.txt' % i

but I don't like the code duplication of f = ....

Is there a pythonic way to avoid the code duplication in this while loop?

NB: I have posted a half-satisfactory solution, using a do/while idiom, as mentioned in the main answer of Emulate a do-while loop in Python?, but I still wonder if there is better way for this particular case (thus, it's not a dupe of this question).

2
  • 1
    glob.glob with some regex would probably be the best way to go. Commented Nov 27, 2018 at 14:35
  • 1
    A nice solution is coming next year: python.org/dev/peps/pep-0572 Commented Nov 27, 2018 at 15:02

5 Answers 5

6

You do not need to follow the while paradiagm here, a nested generator expression with next() works:

import os
from itertools import count
f = next(f for f in ('myfile%04i.txt' % i for i in count()) if not os.path.exists(f))
print(f)
Sign up to request clarification or add additional context in comments.

3 Comments

Perfect solution (I just edited so that we can easily test it by copying/pasting).
@Basj ok, note I just edited it a bit to correct a mistake (of mine)
This is really pythonic, concise, and explicit! I thought it would be possible with a generator / next() but I didn't find how to do it, thanks a lot!
3

Get rid of the f variable.

import os

i = 0
while os.path.exists('myfile%04i.txt' % i):
    i += 1

5 Comments

Oh great! But I still need f at the end, is there a way to get it?
Make f a variable and "give" it to while.
@Basj Yes, you could still initialize f before the loop, then use while os.path.exists(f % i)
The second solution doesn't work, if you print f, you'll get myfile%04i.txt and not myfile0002.txt for example. So we would need to add f = f % i at the end to really get the answer in f. It's probably the best solution so far though!
Ah, you're right. My bad for not running it. I'm going to revert my edit, since that's essentially what you started with.
0

I nearly found the answer while writing the end of the question. After a few modifications, it works:

import os
i = 0
while True:
    f = 'myfile%04i.txt' % i
    if not os.path.exists(f):
        break
    i += 1
print f

Still I wonder if there is a more pythonic way, maybe with an iterator, generator, next(...) or anything like this.

Comments

0

Is this too simple?

import os
f = 'myfile0000.txt'
while os.path.exists(f):
    i += 1
    f = 'myfile%04i.txt' % i

1 Comment

It "works", like my question's code, and the solution I posted, but I wanted to know if there is a solution without duplication of f = ....
0

You could do:

import os
from itertools import count

cursor = count()
it = iter((path for path in map(lambda x: 'myfile%04i.txt' % x, cursor) if not os.path.exists(path)))
first = next(it, None)

if first:
    print(first)

Output

myfile0000.txt

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.