0から100から0(など)までカウントアップし、ループ内の収束基準が満たされたときにのみ停止する無限ループを作成したいので、基本的には次のようになります。
for i in range(0, infinity):
for j in range(0, 100, 1):
print(j) # (in my case 100 lines of code)
for j in range(100, 0, -1):
print(j) # (same 100 lines of code as above)
Jの2つのforループを1つにマージして、ループ内に同じコードを2回書き込む必要がないようにする方法はありますか?
chain
のitertools
メソッドを使用します
_import itertools
for i in range(0, infinity):
for j in itertools.chain(range(0, 100, 1), range(100, 0, -1)):
print(j) # (in my case 100 lines of code)
_
@Chepnerが示唆しているように、無限ループにはitertools.cycle()
を使用できます。
_from itertools import cycle, chain
for i in cycle(chain(range(0, 100, 1), range(100, 0, -1))):
....
_
他の答えと同様に、少しの数学を使用できます:
while(True):
for i in range(200):
if i > 100:
i = 200 - i
さらに別の可能性があります。
while notConverged:
for i in xrange(-100, 101):
print 100 - abs(i)
コードの繰り返しセットがある場合は、関数を使用してスペースと労力を節約します。
def function(x, y, x, num_from_for_loop):
# 100 lines of code
while not condition:
for i in range(1, 101):
if condition:
break
function(x, y, z, i)
for i in range(100, 0, -1):
if condition:
break
function(x, y, z, i)
while True
を使用することもできます
Python 3.5+を使用している場合、一般的な解凍を使用できます。
for j in (*range(0, 100, 1), *range(100, 0, -1)):
またはPython 3.5では、itertools.chain
:
from itertools import chain
...
for j in chain(range(0, 100, 1), range(100, 0, -1)):
up = True # since we want to go from 0 to 100 first
while True: #for infinite loop
# For up == True we will print 0-->100 (0,100,1)
# For up == False we will print 100-->0 (100,0,-1)
start,stop,step = (0,100,1) if up else (100,0,-1)
for i in range(start,stop,step):
print(i)
up = not up # if we have just printed from 0-->100 (ie up==True), we want to print 100-->0 next so make up False ie up = not up( True)
# up will help toggle, between 0-->100 and 100-->0
def up_down(lowest_value, highest_value):
current = lowest_value
delta = 1
while True: # Begin infinite loop
yield current
current += delta
if current <= lowest_value or current >= highest_value:
delta *= -1 # Turn around when either limit is hit
これはジェネレーターを定義し、必要な限り値を生成し続けます。例えば:
>>> u = up_down(0, 10)
>>> count = 0
>>> for j in u:
print(j) # for demonstration purposes
count += 1 # your other 100 lines of code here
if count >= 25: # your ending condition here
break
0
1
2
3
4
5
6
7
8
9
10
9
8
7
6
5
4
3
2
1
0
1
2
3
4
これは、質問に対する直接的な答えというよりも部分的な答えですが、三角関数とその振動の概念を使用して「前後」ループを模倣することもできます。
振幅が100のcos関数があり、f(x) = 0
および0 <= f(x) <= 100
になるように左上にシフトしている場合、式f(x) = 50(cos(x-pi)+1)
(グラフのプロット here 。範囲は必要なものであり、振動が発生するため、値を無効にする必要はありません。
>>> from math import cos, pi
>>> f = lambda x: 50*(cos(x-pi)+1)
>>> f(0)
0.0
>>> f(pi/2)
50.0
>>> f(pi)
100.0
>>> f(3*pi/2)
50.0
>>> f(2*pi)
0.0
もちろん問題は、関数が整数値をそれほど簡単に与えないということです。したがって、それはあまり役に立ちません。しかし、これは、三角関数が彼らのケースに役立つかもしれない将来の読者にとって役に立つかもしれません。
無限の三角波の形で値を作成したいが、いくつかの値をステップオーバーしたいという、以前に似たような問題がありました。私は最終的にジェネレーターを使用することになりました(他の範囲関数も使用しています):
def tri_wave(min, max, step=1):
while True:
yield from range(min, max, step)
yield from range(max, min, -1 * step)
最小、最大、およびステップで慎重に選択された値(つまり、割り切れる)を使用して、
for value in tri_wave(0, 8, 2):
print(value, end=", ")
最小値と最大値を取得するのは一度だけで、これが私の目標でした:
...0, 2, 4, 6, 8, 6, 4, 2, 0, 2, 4, 6, 8, 6, 4...
私はPython 3.6を使用していました。
条件や列挙なしでこの種の三角形オシレーターを実装できるかどうか興味がありました。 1つのオプションは次のとおりです。
_def oscillator(magnitude):
i = 0
x = y = -1
double_magnitude = magnitude + magnitude
while True:
yield i
x = (x + 1) * (1 - (x // (double_magnitude - 1))) # instead of (x + 1) % double_magnitude
y = (y + 1) * (1 - (y // (magnitude - 1))) # instead of (y + 1) % magnitude
difference = x - y # difference ∈ {0, magnitude}
derivative = (-1 * (difference > 0) + 1 * (difference == 0))
i += derivative
_
この背後にある考え方は、異なる周期の2つのノコギリ波を取得し、互いに引き算することです。結果は、値が{0、itude}の方形波になります。次に、ターゲット信号の微分値を取得するために、それぞれ{0、マグニチュード}を{-1、+1}に置き換えます。
_magnitude = 5
_の例を見てみましょう:
_o = oscillator(5)
[next(o) for _ in range(21)]
_
これは_[0, 1, 2, 3, 4, 5, 4, 3, 2, 1, 0, 1, 2, 3, 4, 5, 4, 3, 2, 1, 0]
_を出力します。
abs()
が許可されている場合は、簡単にするために使用できます。たとえば、次のコードは上記と同じ出力を提供します。
_[abs(5 - ((x + 5) % 10)) for x in range(21)]
_