作業中にメモリ不足の例外が発生しましjavax.Swing
た。これが私がしたことです。16 個の jpg (それぞれ 70*70 ピクセル) をロードし、16 個ありましたJbuttons
。ImageIcon
ループ内でJButtons
をさまざまな jpg に非常に迅速に設定します。基本的に、CPU が処理できるのと同じ速さです。メモリ使用量が大幅に増加します。問題は、画像をリロードしたことがないことです。画像は 16 枚しかなく、すべての割り当ては参照によって渡されます。Eclipse Memory Analyzer を実行したところ、次の結果が得られました。
" < システム クラス ローダー > " によってロードされる "java.awt.image.FilteredImageSource" の 1 つのインスタンスは、703,066,368 (43.58%) バイトを占有します。インスタンスは、sun.awt.image.ToolkitImage @ 0x7859cef60 によって参照され、「 < system class loader > 」によってロードされます。メモリは、「< システム クラス ローダー >」によってロードされた「java.util.Hashtable$Entry[]」の 1 つのインスタンスに蓄積されます。
キーワード java.awt.image.FilteredImageSource
java.util.Hashtable$Entry[]
Java のスイング実装にメモリ リークがあるのではないかと疑うことはできますか? 何か案は?
基本的に、コードは次のようになります。
public class Test{
private static ImageIcon[] imgIcon;
private static JButton[] buttons;
private static JFrame myFrame;
public static void main(String[] args){
myFrame = new JFrame(new GridLayout());
for(int i = 0; i < 16; i ++){
imgIcon[i] = //load the imageIcons
buttons[i] = new JButton();
myFrame.add(buttons[i]);
}
myFrame.pack();
myFrame.setVisible(true);
new Thread(new Runnable(){
@Override
public void run(){
while(true){
for(int i = 0; i < 16; i ++){
SwingUtilities.invokeAndWait(new Runnable(){
public void run(){
buttons[i].setIcon(imgIcon[/*random num 1-16*/]);
});
}
}
}
}).start();
}
}
新しいスレッドで行われている多くのことを抽象化したので、ここでは明らかなアンチパターンを無視してください。