2017-02-28 8 views
0

私はgeoJSONファイルを持っています。このファイルには、特定の地理的エリアのca. 7000細胞。 a)このgeoJSONを開くb)いくつかのデータを変更する(コードを参照)c)この変更されたgeoJSONをディスクに書き込む。今、私の問題は、多くの細胞があるので、これにはほぼ1分かかります。この機能の速度を向上させる方法はありますか?ありがとうございました!Python - 読み取り/変更/書き込み速度を上げますか?

def writeGeoJSON(param1, param2, inputdf): 
    with open('ingeo.geojson') as f: 
     data = json.load(f) 
    for feature in data['features']: 
     currentfeature = inputdf[(inputdf['SId']==feature['properties']['cellId']) & (inputdf['param1']==param1) & (inputdf['param2']==param2)] 
     if (len(currentfeature) > 0): 
      feature['properties'].update({"style": {"opacity": currentfeature.Opacity.item()}}) 
     else: 
      feature['properties'].update({"style": {"opacity": 0}}) 
    end = time.time() 
    with open('outgeo.geojson', 'w') as outfile: 
     json.dump(data, outfile) 
+1

は多分[(inputdf [ 'のparam1'] ==のparam1 inputdf '計算:


はCPythonのと仮定すると、より良い)、私はこれが良い(より良い許可よりも許し)を求めることを期待します)&(inputdf ['param2'] == param2)] 'のようになります。 –

+0

最初に、[プロファイル](http://stackoverflow.com/a/582337/3005167)ボトルネックがI/Oにあるか処理中であるかを調べる機能。他の何もかもが暗闇の中でただ釣っているだけです。 – kazemakase

+0

@Alex Excellent!私は私の答えに同じ点を述べました。私は質問が投稿された瞬間に気付いた...私は携帯電話からこの質問に答えるために9分を取った! xD – varun

答えて

2

あなたのコード内で可能シリアルコードの最適化があります。最後の2つのチェックがforループの外に置くことができることを

currentfeature = inputdf[(inputdf['SId']==feature['properties']['cellId']) & (inputdf['param1']==param1) & (inputdf['param2']==param2 

注意:あなたはラインを持っています。 forループ内の各繰り返しで多くのCPUクロックサイクルを費やす冗長チェックです。 あなたが同じ変更できます。あなたのプログラムがはるかに高速に実行しなければならない

paramMatch=inputdf['param1']==param1 & inputdf['param2']==param2 
for feature in data['features']: 
    currentfeature = inputdf[(inputdf['SId']==feature['properties']['cellId']) & paramMatch] 

言い換えれば、より良い実行時間が必要な場合は、ほとんどの場合、必ずmultiprocessingモジュールを使用してコードの処理部分を並列化してみてください。 forループで作業負荷を分割しようとすることができます。

繰返しブロックにapply_asyncまたはmap_asyncを使用して試してみてください。 [最適化を@varunに加えて、および@のロマンAGAの提案を含む。]

+0

ありがとう、その60%カット時間を実行!私はそれを並行して実行しようとします。 :) –

+0

恐ろしい!あなたがCpython(デフォルトのPythonディストリビューション)を使っているなら、 'Threading'モジュールを避け、' multiprocessing'モジュールを使用してください。そうでなければ、それもオプションになります! – varun

+1

ええ私はいくつかのユニ・アサインメントで前に 'マルチプロセッシング 'を行ってきました。だから私はおなじみです:)私が知っている限り、' threading'はGILの実際の並列計算を行いません。 :) –

1

関数の先頭にこれを追加します。

zero_style = {"opacity": 0} 

となることが条件を変更:

if (len(currentfeature) > 0): 
    feature['properties']['style'] = {"opacity": currentfeature.Opacity.item()} 
else: 
    feature['properties']['style'] = zero_style 

私は多分if currentfeature:を指示(詳細についてinputdfタイプは、より良い最適化につながる知ることは多分ありますか?十分であるという印象を持っています?

try: 
    value = {"opacity": currentfeature.Opacity.item()} 
except NotSureWhatExceptionMaybeAttributeError: 
    value = zero_style 
feature['properties']['style'] = value 
+0

+1。これは、各繰り返しでのPython辞書作成オーバーヘッドの興味深い洞察です。私は実験し、違いがあるかどうかを確認します。私はそれが少し速くなると思う! :) – varun

関連する問題