Ich machte ein kleines funktionierendes Beispielprogramm für das Problem, das ich habe. Bitte daran denkt, dass mein wirkliches Programm komplexer ist und alle diese Klassen benötigt werden, auch wenn es in dieser kleinen StichprobeTableView aktualisiert nicht auf neuen Informationen von Threads
Hauptklasse überdimensionierte sieht:
public class PingTest extends Application {
private static final ArrayList<PingThread> THREADS = new ArrayList();
@Override
public void start(Stage primaryStage) {
AnchorPane root = new AnchorPane();
TableView<Map.Entry<String, Ping>> tblPing = new TableView();
TableColumn<Map.Entry<String, Ping>, String> colName = new TableColumn("Name");
TableColumn<Map.Entry<String, Ping>, String> colTime = new TableColumn("Time");
TableColumn<Map.Entry<String, Ping>, String> colDifference = new TableColumn("Difference");
colName.setCellValueFactory((TableColumn.CellDataFeatures<Map.Entry<String, Ping>, String> p) -> new SimpleStringProperty(p.getValue().getKey()));
colTime.setCellValueFactory((TableColumn.CellDataFeatures<Map.Entry<String, Ping>, String> p) -> new SimpleStringProperty(Integer.toString(p.getValue().getValue().getTime())));
colDifference.setCellValueFactory((TableColumn.CellDataFeatures<Map.Entry<String, Ping>, String> p) -> new SimpleStringProperty(Integer.toString(p.getValue().getValue().getDifference())));
ObservableList<Map.Entry<String, Ping>> items = FXCollections.observableArrayList(Pings.getPings().entrySet());
tblPing.setItems(items);
Scene scene = new Scene(root, 300, 750);
// Align to pane
AnchorPane.setTopAnchor(tblPing, 0.0);
AnchorPane.setLeftAnchor(tblPing, 0.0);
AnchorPane.setRightAnchor(tblPing, 0.0);
AnchorPane.setBottomAnchor(tblPing, 0.0);
tblPing.getColumns().addAll(colName, colTime, colDifference);
root.getChildren().add(tblPing);
// Setting primary Stage
primaryStage.setOnCloseRequest(e -> {
THREADS.forEach(t -> t.interrupt());
});
primaryStage.setTitle("Ping List");
primaryStage.setScene(scene);
primaryStage.show();
}
public static void main(String[] args) {
// Some examples
String[] servers = {"www.google.com", "www.bing.com", "www.yahoo.com", "www.stackoverflow.com"};
// Start Threads
for (String server : servers) {
PingThread pingThread = new PingThread(server);
pingThread.start();
THREADS.add(pingThread);
}
launch(args);
}
}
Helper Class
public class Ping {
private int difference;
private int time;
private final String url;
public Ping(String url,int time) {
this.url = url;
this.time = time;
difference = 0;
}
public int getDifference() {
return difference;
}
public int getTime() {
return time;
}
public void setTime(int time) {
difference = time - this.time;
this.time = time;
}
public String getUrl() {
return url;
}
}
Themen
public class PingThread extends Thread {
private final String SERVER;
private int ping = 0;
public PingThread(String server) {
SERVER = server;
}
@Override
public void run() {
try {
while (true) {
// Ping, update then sleep
ping();
Pings.update(SERVER, ping);
Thread.sleep(1000);
}
} catch (InterruptedException ex) {
// Used to end thread
}
}
public void ping() {
try {
// Sendinging request
InetAddress host = InetAddress.getByName(SERVER);
long tm = System.nanoTime();
Socket so = new Socket(host, 80);
so.close();
ping =(int)((System.nanoTime() - tm)/1000000L);
} catch (IOException ex) {
}
}
}
Data Container
public class Pings {
private static final ConcurrentHashMap<String,Ping> PINGS= new ConcurrentHashMap();
public static synchronized void update(String server, int time) {
if (PINGS.containsKey(server)) {
PINGS.get(server).setTime(time);
} else {
PINGS.put(server, new Ping(server,time));
}
}
public static synchronized ConcurrentHashMap<String,Ping> getPings(){
return PINGS;
}
}
Die GUI-Tabelle ist nicht auf neue Werte zu aktualisieren, in meiner größeren Implementierung wie in diesem kleinen Beispiel. Was mache ich falsch, wenn ich die Werte an TableView anbinde?
Vielen Dank für Ihre umfassende Erklärung – chenino