2012-02-10 59 views
2

私はそれを滑らかに保ちながらアップスケーリングする必要があるRGBAイメージを持っています。Pythonの2D配列よりスライディングウィンドウでモードを計算する最も効率的な方法は何ですか?

キャッチすることは、色を正確に維持する必要があることです(バックグラウンド:地方が色分けされたマップのサイズを変更しています)ので、バイキュービック補間でサイズ変更を行うことはできません。平滑化中に画素の色を補間する。

こうして、スムーズなエッジを得るためには、最も近いネイバー(私に階段パターンを与えて)を使って高級化し、ターゲット画像の各ピクセルをaで最も頻繁に発生するピクセル色に置き換えてエッジを丸めることを望んでいました一定の半径なので、ラ:それは動作しないことを除いてPILのImageFiltersは、各チャンネルに個別に操作するように、これは、かなり迅速に終了

from PIL import Image, ImageFilter 
amount=3 
image=Image.open(<file>) 
image=image.filter(ImageFilter.ModeFilter(amount)) 

dest[x,y]=Counter([tuple(e) for e in reshape(source[max(x-r,0):x+r+1,max(y-r,0):y+r+1],(-1,4))]).most_common()[0][0] 

注ここでDESTとソースが故に必要整形及びタプルに変換し、同じ形状XxYx4アレイであること:私はnumpyの配列に頼るとループで次の操作を実行しようとした拳

を振ります。
これは理論的にはうまくいくが、私が操作している画像は画像のの画像には12時間かかります。私は、これが主に鋳造と再形成の不必要なオーバーヘッドに起因すると推測しています。

これをPythonで行う適切な方法は何でしょうか?

私は自分の手を捨てて、この作業を行うためのC++モジュールを書く準備ができています。
私はこの道から私を遠ざけることは何でもありがとう!

+0

あなたはこれを見たことがありますか?私は同じような画像処理タスクの前に数回インラインC++に頼らざるを得ませんでした。もしあなたが8200万画素を見ているなら、これはC++の重い吊り上げのための優れた候補のようです。 [PerformancePython](http://www.scipy。org/PerformancePython) – Ancallan

+1

通常、numpy配列の操作を高速化する必要があったとき、私はnumpyにすべての作業を処理させる巧妙な方法を見つけようとしたか、またはPythonイテレータを使用しました。 2番目のコードスニペットで何が起こっているのかを知ることは難しいです。より小さな配列の簡単な例を提供できますか? – user545424

+0

@Ancallanそのリンクは目を見張るものでした。私はいくつかのCを投げつけてインライン展開し、x500のスピードアップを達成しました。あなたのコメントが解決策だったら私はそれを受け入れます。 scipyやコンパイラにアクセスできる人に頼らなければならないという問題がまだ残っていますが、私はそれで暮らすことができると思います! – megawidget

答えて

1

画像に固定された色が気になる場合は、「パレット」画像モードが適しています(少なくとも、マップに256色以上の色がない場合)。

あなたの画像を「P」モードに変換することをお勧めします(私はPILに精通していないので、わかりませんが、簡単です)。おそらくパレットを明示的に構築する必要がありますモードフィルタを適用します。

私の頭に浮かび上がるもう一つの解決策は、アップサイジングのときにバイキュービック補間を使用して元のイメージから派生したパレットを使用してパレットイメージに変換することです。これにより、現在のアプローチよりも優れた結果が得られる(実装が簡単になる)かもしれません。

+0

ああ、2000色以上あります。 この解決法は他には素晴らしいことでした。 – megawidget

-1

Image_scalingに記載されているEPXは新しい色を導入していません。スケール2xはこれを行います:

A --\ 1 2 
C P B --/ 3 4 
    D 

IF C==A => 1=A 
IF A==B => 2=B 
... 

また、スケール3xも記述されています。
それとは別に、私は「まっすぐC」に同意します。あなたが知っていることに依存します。 誰でもnp_inlineを使っていますか?

関連する問題