2017-08-02 6 views
-2

Rhino/Grasshopper用のGyPythonコンポーネントを使用した簡単なスクリプトがあります。目標は、1時間ごとの気象データ(数時間しか記録されていない)を時間に割り当てることです。加え大きなデータセットでPythonスクリプトがクラッシュする

hoursList = [hr1,hr2,hr3,hr4,hr5,hr6] 
measuredList = [hr2,hr3,hr6] 
recordList = [wData1,wData2,wData3] 
finalList = []  

def assignData(i,y):   
    for i < len(leadList):    
     if hoursList[i] == measuredList[y]:     
      finalList.append(recordList[y])     
      i += 1 
      y += 1     
     else:     
      finalList.append(0)     
      i += 1  
     assignData(i,y)  

i = 0 
y = 0  
assignData(i,y) 

べきリターン

[0,wData1,wData2,0,0,wData3] 

(この場合のfinalListを得改行:それは0を返すない測定がなかった場合は、この(同様の値を有する例)のように動作するはず

[0, 'wData1', 'wData2', 0, 0, 'wData3', 'wData3', 
0, 'wData3', 'wData3', 0, 0, 'wData3', 'wData3', 
0, 'wData3', 'wData3', 'wData2', 0, 0, 'wData3', 'wData3', 
0, 'wData3', 'wData3', 0, 0, 'wData3', 'wData3', 
0, 'wData3', 'wData3', 'wData1', 'wData2', 0, 0, 'wData3', 'wData3', 
0, 'wData3', 'wData3', 0, 0, 'wData3', 'wData3', 
0, 'wData3', 'wData3', 'wData2', 0, 0, 'wData3', 'wData3', 
0, 'wData3', 'wData3', 0, 0, 'wData3', 'wData3', 
0, 'wData3', 'wData3'] 

大きなデータリスト(約43000値)でこのコードを実行しようとすると、後でクラッシュします約7000反復。私はsys.getrecursionlimitをチェックし、それは2147483647だ。このアイデアを得るにはどんなアイデア?

+0

ようこそStackOverflow。ヘルプドキュメントの投稿ガイドラインを読み、それに従ってください。 [最小、完全で検証可能な例](http://stackoverflow.com/help/mcve)がここに適用されます。 MCVEコードを投稿して問題を正確に記述するまでは、効果的にお手伝いすることはできません。 投稿したコードをテキストファイルに貼り付け、説明した問題を再現できるはずです。 特に、あなたは 'leadList'を与えていません - より良いことに、与えられた変数から長さを導出するだけでよいので、コードを実行することができます。 – Prune

+0

また、コードが機能しないことに注意してください。あなたが記述する方法にとどまらず、それがまったく実行されない構文エラーがあります。それは何も返さない*。むしろ、グローバルリストを副作用として変更します。これは、あなたが私たちに見せてもらうために気にしていないものです。 – Prune

+0

とりわけ、6要素のデータセットにはどのような出力がありますか?私の例ではそれを見ることができますが、これは説明する*あなたの問題であるはずです。 – Prune

答えて

2

ANALYSIS

私はlen(leadList)はあなたが与える43000数字であることを収集します。私はこれをlimitと呼ぶでしょう。あなたのループがどのように動作するか

注:limitに「I入力」の範囲内iのすべての値について、これは一つの項目、刻みi(そしておそらくy)を処理し、再発します。したがって、i=0の最上位レベルのコールは、assignData(1, 0)(失敗したと仮定)へのコールを生成し、それが完了するまで待機します。それから、ループの先頭に戻り、i = 1で作業を続け、最後にlimitの再帰呼び出しを連続して生成します。

最初の呼び出しでは範囲(1、限度)が機能し、limit-1呼び出しが発生します。最初の呼び出しではlimit-2呼び出しが発生します。各レベルでは、大きなファンアウトを持つ別のレベルが生成されます。

要するに、私が思うよりもはるかに多くの通話が発生します。 limitを増やすと、合計がかなり速くなります。

これらの呼び出しのそれぞれが1つの要素を追加するため、finalListは利用可能なメモリを単に超えるだけであると思われます。

INVESTIGATION

はあなたのコードに基本的なデバッグ文を挿入します

def assignData(i, y): 
    print "ENTER", i, y, finalList 
    for i < len(leadList): 
     ... 

だからあなたは通話の進行状況を確認することができます。

修理

私はあなたがこの二重にネストされた再帰スタックが必要であることを疑います。実際、私は再帰があなたに何かを買うのを見ません。あたかもリストを1回歩いて実際に対応している時間を見つけ、それ以外の場合は0を書き込む必要があるかのように見えます。呼び出しを取り除き、forを適切に使用してiの値を制御し、適切なコードを削除します。

def assignData(): 
    y = 0   
    for i in range(0, len(leadList)):    
     if hoursList[i] == measuredList[y]:     
      finalList.append(recordList[y])     
      y += 1     
     else:     
      finalList.append(0) 

よりよい解決策

あなたが必要とするすべてが一致する時間のレコードである場合は、これはさらに直接行うことができます。時間からの測定値を索引付けするための辞書を作成します。

meas = dict(zip(measuredList, recordList) 

ここでは、辞書に含まれていない任意の時間に0を挿入するようにリストの理解度を書きます。

finalList = [meas[time] if time in meas else 0 
       for time in hourslist] 

問題を正しく読んでいれば、それが全体的な目標です。

関連する問題