Определенно есть лучшие способы сделать это, но если вы хотите сделать это с помощью цикла, это сработает.
item = '%1 greets %0'
args = ['bob','alex']
loc = 0
for x in item:
if x == "%":
loc = item.find("%",loc)
val ='%'+ item[loc +1]
index = int(item[loc +1])
replace = args[index]
item = item.replace(val,replace)
loc +=1
print(item)
Ваше решение не работает, потому что вы продолжаете искать ту же строку (формат), но сохраняете результат в другой строке (str). Поэтому метод find всегда найдет первый% в строке формата.
Еще один комментарий, который я хотел бы добавить, - избегать именования ваших переменных в качестве ключевых слов python, таких как format и str.