Вот альтернативный способ сделать это без секунды для цикла:
sequences = [ 1, 1, 2, 5, 9, 18 ]
multipliers = [ 36, 72, 144, 288, 576, 1152 ]
for x in range(100):
print(*sequences)
sequences = [ s + m*64**x for s,m in zip(sequences,multipliers) ]
[РЕДАКТИРОВАТЬ] Глядя на значения, я заметил, что эту конкретную последовательность также можно получить с помощью:
N [i + 1] = 2 * N [i] + (-1,0,1 по очереди)
или
N [i + 1] = 2 * N [i]+ i mod 3 - 1 (при условии индекса на основе нуля)
i N[i] [-1,0,1] N[i+1]
0 1 -1 --> 2*1 - 1 --> 1
1 1 0 --> 2*1 + 0 --> 2
2 2 1 --> 2*2 + 1 --> 5
3 5 -1 --> 2*5 - 1 --> 9
4 9 0 --> 2*9 + 0 --> 18
...
Таким образом, более простой цикл для создания последовательности может быть:
n = 1
for i in range(100):
print(n)
n = 2*n + i % 3 - 1
ИспользованиеФункция Reduction от functools может сделать это еще более кратким:
from functools import reduce
sequence = reduce(lambda s,i: s + [s[-1]*2 + i%3 - 1],range(20),[1])
print(sequence)
>>> [1, 1, 2, 5, 9, 18, 37, 73, 146, 293, 585, 1170, 2341, 4681, 9362, 18725, 37449, 74898, 149797, 299593, 599186]
Используя ваш многоканальный подход и мою предложенную формулу, это даст:
sequences = [ 1, 1, 2, 5, 9, 18 ]
multipliers = [ 36, 72, 144, 288, 576, 1152 ]
allSequences = reduce(lambda ss,x: ss + [[ s + m*64**x for s,m in zip(ss[-1],multipliers) ]],range(100),[sequences])
for seq in allSequences: print(*seq) # print 6 by 6
[EDIT2] Если все ваши последовательностибудет иметь похожий шаблон (т. е. стартовые каналы, множители и формулу расчета), вы можете обобщить печать таких последовательностей в функции, поэтому для каждой последовательности требуется только одна строка:
def printSeq(calcNext,sequence,multipliers,count):
for x in range(count):
print(*sequence)
sequence = [ calcNext(x,s,m) for s,m in zip(sequence,multipliers) ]
printSeq(lambda x,s,m:s*2+m*64**x,[1,1,2,5,9,18],multipliers=[36,72,144,288,576,1152],count=100)
[EDIT3] Улучшениев функции printSeq.
Я считаю, что вам не всегда понадобится массив множителей для вычисленияследующее значение в каждом канале.Улучшение функции будет заключаться в предоставлении индекса канала для лямбда-функции вместо множителя.Это позволит вам использовать массив множителей, если вам нужно, но также позволит вам использовать более общие вычисления.
def printSeq(name,count,calcNext,sequence):
p = len(sequence)
for x in range(count):
print(name, x,":","\t".join(str(s) for s in sequence))
sequence = [ calcNext(x,s,c,p) for c,s in enumerate(sequence) ]
Функция лямбда имеет 4 параметра и, как ожидается, вернет следующую последовательностьзначение для указанного канала:
s : current sequence value for the channel
x : iteration number
c : channel index (zero based)
p : number of channels
Таким образом, использование массива внутри формулы будет выражать его следующим образом:
printSeq("A077947",100,lambda x,s,c,p: s + [36,72,144,288,576,1152][c] * 64**x, [1,1,2,5,9,18])
Но вы также можете использовать более общую формулу, основанную напо индексу каналов (и количеству каналов):
printSeq("A077947",100,lambda x,s,c,p: s + 9 * 2**(p*x+c+2), [1,1,2,5,9,18])
или (6 каналов на основе 2 * S + i% 3 - 1):
printSeq("A077947",100,lambda x,s,c,p: 64*s + 9*(c%3*2 - (c+2)%3 - 1) ,[1,1,2,5,9,18])
printSeq("A077947",100,lambda x,s,c,p: 64*s + 9*[-3,1,2][c%3],[1,1,2,5,9,18])
Мои рассуждения здесь таковычто если у вас есть функция, которая может вычислить следующее значение на основе текущего индекса и значения в последовательности, вы сможете определить пошаговую функцию, которая будет вычислять значение, равное N индексам дальше.
УчитываяF (i, S [i]) -> i + 1, S [i + 1]
F2(i,S[i]) --> i+2,S[i+2] = F(F(i,S[i]))
F3(i,S[i]) --> i+3,S[i+3] = F(F(F(i,S[i])))
...
F6(i,S[i]) --> i+6,S[i+6] = F(F(F(F(F(F(i,S[i]))))))
...
Fn(i,S[i]) --> i+n,S[i+n] = ...
Это всегда будет работать и не должно требовать массив множителей.В большинстве случаев должно быть возможно упростить Fn, используя простую алгебру.
, например, A001045: F (i, S) = i + 1, 2 * S + (-1) ** i
printSeq("A001045",20,lambda x,s,c,p: 64*s + 21*(-1)**(x*p+c),[0,1,1,3,5,11])
Обратите внимание, что начиная с 3-го значения, следующее значение в этой последовательности может быть вычислено без знания индекса:
A001045: F (S) = 2 * S + 1 - 2 * 0** ((S + 1)% 4) * +1056 *