0

私はここで、私が抱えているが解決できないさらに別の論理的な問題を提起します!

私はここにこのクラスを持っています:

package data;

import gui.GUIJuego;

import java.util.Random;
import java.util.Timer;
import java.util.TimerTask;

import dominio.Adorno;
import dominio.EdificioNoPublico;
import dominio.EdificioPublico;
import dominio.Item;

public class Administrador {

private Ciudad ciudad;
private int contadorExplosion;
private boolean endofgame;
private Dificultad dificultad;
private Constructora constructora;

public Administrador(Ciudad ciudad, int contadorExplosion, boolean endofgame, Dificultad dificultad, Constructora constructora) {
    this.ciudad = ciudad;
    this.contadorExplosion = contadorExplosion;
    this.endofgame = endofgame;
    this.dificultad = dificultad;
    this.constructora = constructora;
}

public Administrador(){
    this.setCiudad(new Ciudad());
    this.setContadorExplosion(0);
    this.setEndofgame(false);
    this.setDificultad(new Dificultad(1));
    this.setConstructora(new Constructora());
}

public void administrar(final GUIJuego juego){

    Timer timer = new Timer("Juego");

    this.setEndofgame(false);

    while(endofgame == false){


        timer.scheduleAtFixedRate(new TimerTask(){
            public void run() {

                juego.getArcaLabel().setText("Arca: " + getCiudad().getArca());
                juego.getPuntosBellezaLabel().setText("Puntos de Belleza: " + getCiudad().getPuntosBelleza());
                juego.getHabitantesLabel().setText("Habitantes: " + getCiudad().getCantidadHabitantes() + " / " + getCiudad().getCantidadHabitantesDisponibles());
                getEgresosIngresos();
                tryExplotar();

            }

        }, 0, 1000);

    }

}

private void getEgresosIngresos(){

    for(Item i : this.getCiudad().getItems()){

        if(i.getContadorTiempo() == 89){

            i.setContadorTiempo(0);

            if(i instanceof EdificioNoPublico)
                this.getCiudad().setArca(this.getCiudad().getArca() + ((EdificioNoPublico) i).getRenta());
            else
                this.getCiudad().setArca(this.getCiudad().getArca() - getCostosAdornosEdificiosPublicos(i));

        } else { i.setContadorTiempo(i.getContadorTiempo() + 1); }
    }

}

private int getCostosAdornosEdificiosPublicos(Item i){

    if(i instanceof EdificioPublico)
        return ((EdificioPublico) i).getCostoMantenimiento();
    else if(i instanceof Adorno)
        return ((Adorno) i).getCostoMantenimiento();

    return 0;
}

private void tryExplotar(){

    if(this.getContadorExplosion() == 299 && this.getCiudad().getItems() != null){

        Random rnd = new Random();

        if(rnd.nextInt(100) < this.getCiudad().getProbabilidadExplosion() && this.getCiudad().getItems().size() > 0){
            this.getCiudad().getItems().remove( rnd.nextInt ( this.getCiudad().getItems().size() ) );
            this.setContadorExplosion(0);
        }

        rnd = null;

    }else{ this.setContadorExplosion(this.getContadorExplosion() + 1); }

}

// ### Getters y Setters ###

public Ciudad getCiudad() {
    return ciudad;
}

public void setCiudad(Ciudad ciudad) {
    this.ciudad = ciudad;
}

public int getContadorExplosion() {
    return contadorExplosion;
}

public void setContadorExplosion(int contadorExplosion) {
    this.contadorExplosion = contadorExplosion;
}

public boolean isEndofgame() {
    return endofgame;
}

public void setEndofgame(boolean endofgame) {
    this.endofgame = endofgame;
}


public Dificultad getDificultad() {
    return dificultad;
}

public void setDificultad(Dificultad dificultad) {
    this.dificultad = dificultad;
}

public Constructora getConstructora() {
    return constructora;
}

public void setConstructora(Constructora constructora) {
    this.constructora = constructora;
}

// ### Fin Getters y Setters ##
}

しかし、皆さんが興味を持っているのは、この特定の方法です。

public void administrar(final GUIJuego juego){

    Timer timer = new Timer("Juego");

    this.setEndofgame(false);

    while(endofgame == false){


        timer.scheduleAtFixedRate(new TimerTask(){
            public void run() {

                juego.getArcaLabel().setText("Arca: " + getCiudad().getArca());
                juego.getPuntosBellezaLabel().setText("Puntos de Belleza: " + getCiudad().getPuntosBelleza());
                juego.getHabitantesLabel().setText("Habitantes: " + getCiudad().getCantidadHabitantes() + " / " + getCiudad().getCantidadHabitantesDisponibles());
                getEgresosIngresos();
                tryExplotar();

            }

        }, 0, 1000);

    }

}

現在、デバッガーで確認できる限り、タイマーはループしており、その内部の関数を実行しようとしていることさえ完全にはわかりません。私が知っているのは、フレーム(パラメーター GUIJuego はスイングフレーム)正常に動作しますが、タイマーがプログラムをすべて停止させています。論理エラーを起こしているのでしょうか、それともタイマーが間違っていると考えていますか?

ここまでお読みいただき、誠にありがとうございました。

4

1 に答える 1

1

忙しい while ループ内で timer.scheduleAtFixedRate を呼び出しています。ほとんどの場合、一度だけ呼び出したいと思うでしょう。

TimerTask を使用すると、実行は別のスレッドで行われます。ここで実際に別のスレッドが必要かどうかはわかりませんが、そうでない場合、あなたがやろうとしていることを実行する最も簡単な方法は

while(!endOfGame) {
   juego.getArcaLabel().setText("Arca: " + getCiudad().getArca());
   juego.getPuntosBellezaLabel().setText("Puntos de Belleza: " + getCiudad().getPuntosBelleza());
   juego.getHabitantesLabel().setText("Habitantes: " + getCiudad().getCantidadHabitantes() + " / " + getCiudad().getCantidadHabitantesDisponibles());
   getEgresosIngresos();
   tryExplotar();

  Thread.sleep(1000);
}

別のスレッドでタイマーを実行する必要がある場合は、ビジー状態の待機 (while) ループよりも、タイマー スレッドの実行が終了するまで待機するためのより適切な方法が必要です。たとえば、thead.join() を使用できますが、タイマーの内部ロジックに依存するのではなく、タイマー スレッドを明示的に作成する必要があります。または、オブジェクトを同期し、wait/notify コンストラクトを使用して、いつ再開するかをメイン スレッドに知らせることができます。

于 2013-11-11T20:15:55.047 に答える