在封闭范围JavaFx中定义的Lambda表达式局部变量文本

在封闭范围JavaFx中定义的Lambda表达式局部变量文本,java,javafx,lambda,scope,minesweeper,Java,Javafx,Lambda,Scope,Minesweeper,我正在使用JavaFX创建一个扫雷游戏。我有一个lambda表达式,其中(目前)当我从按钮网格中按下按钮时,它将按钮的文本设置为二维数组中的位置。我得到的错误是“在封闭范围内定义的局部变量文本必须是final或实际上是final。” 我知道我在lambda表达式中使用的变量无法完成,因为它们必须是表达式外部的最终变量。但我不知道该怎么解决这个问题 static Stage stage; Button[][] buttonGrid; public void start(Stage primary

我正在使用JavaFX创建一个扫雷游戏。我有一个lambda表达式,其中(目前)当我从按钮网格中按下按钮时,它将按钮的文本设置为二维数组中的位置。我得到的错误是“在封闭范围内定义的局部变量文本必须是final或实际上是final。”

我知道我在lambda表达式中使用的变量无法完成,因为它们必须是表达式外部的最终变量。但我不知道该怎么解决这个问题

static Stage stage;
Button[][] buttonGrid;

public void start(Stage primaryStage) throws Exception {
    SetSettings.readSettings();
    GridPane gridpane = new GridPane();

    int gridSize = Minesweeper.gridSize;
    buttonGrid = new Button[gridSize][gridSize];
    for (int i = 0; i < gridSize; i++) {
        for (int j = 0; j < gridSize; j++) {
            buttonGrid[i][j] = new Button();
            GridPane.setConstraints(buttonGrid[i][j], j, i);

        }
    }
    String text = "";
    for (int i = 0; i < gridSize; i++) {
        for (int j = 0; j < gridSize; j++) {
            text += i + "" + j;
            buttonGrid[i][j].setOnAction(e -> {
                buttonGrid[i][j].setText(text);
                text = "";

            });
            gridpane.getChildren().add(buttonGrid[i][j]);
        }
    }

    stage = primaryStage;
    primaryStage.setOnCloseRequest(e -> {
        e.consume();
        ConfirmExit.display("Exit", "Are you sure you want to quit this game?");
    });
    primaryStage.setTitle("Minesweeper");
    stage.getIcons().add(new Image("/Logo.jpg"));
    Scene scene = new Scene(gridpane, 600, 500);
    primaryStage.setScene(scene);
    primaryStage.show();
}


public static void main(String[] args) {
    launch(args);
}
静态阶段;
按钮[][]按钮栅格;
public void start(Stage primaryStage)引发异常{
SetSettings.readSettings();
GridPane GridPane=新建GridPane();
int gridSize=扫雷舰.gridSize;
buttonGrid=新按钮[gridSize][gridSize];
对于(int i=0;i{
buttonGrid[i][j].setText(文本);
text=“”;
});
gridpane.getChildren().add(buttonGrid[i][j]);
}
}
阶段=初级阶段;
primaryStage.setOnCloseRequest(e->{
e、 消费();
显示(“退出”,“您确定要退出此游戏吗?”);
});
初级阶段。设置标题(“扫雷舰”);
stage.getIcons().add(新图像(“/Logo.jpg”);
场景=新场景(网格窗格,600500);
初级阶段。场景(场景);
primaryStage.show();
}
公共静态void main(字符串[]args){
发射(args);
}
它在同一个错误中标记i、j和文本

gridSize是我的扫雷舰网格的大小。buttonGrid是我放置在gridPane中的按钮网格


我在stackoverflow上看到了一个将这些变量设置为全局变量的解决方案,但这不起作用

只需将
文本的定义移动到循环内部(这样,您就可以在循环的每次迭代中定义一个新的、有效的最终变量)。您也可以用同样的方法定义
按钮
变量,以避免引用
i
j

for (int i = 0; i < gridSize; i++) {
    for (int j = 0; j < gridSize; j++) {
        String text = i + "" + j;
        Button button = buttonGrid[i][j] ;
        button.setOnAction(e -> {
            button.setText(text);    
        });
        gridpane.getChildren().add(buttonGrid[i][j]);
    }
}
for(int i=0;i{
按钮.setText(文本);
});
gridpane.getChildren().add(buttonGrid[i][j]);
}
}

那么,如果我制作了一个新按钮,我如何添加i和j的值呢?@SakshamGoyal我不明白你所说的“添加
i
j
的值”是什么意思。这段代码没有创建任何新按钮。在OP中添加了完整的代码。你明白我在npw中尝试做什么吗?@SakshamGoyal我真的不明白你在字符串连接中尝试做什么,或者你为什么要在事件处理程序中重置
文本
。不清楚你预计那里会发生什么。当按下按钮(I,j)时,你想在按钮(I,j)中显示什么文本?你说:“当我按下按钮网格中的一个按钮时,它会将文本设置为2D数组中的位置”,这就是我发布的代码所做的。java中没有“全局”,即使你将变量转换为字段,这也不会起作用。我不知道你想在这里实现什么,但即使假设你将结果复制到内部循环/创建字段中的新变量,逻辑似乎很奇怪:第一次单击按钮时,该按钮的文本将更改为包含所有索引组合,对于文本删除后发生的所有点击…@fabian我已经添加了我的完整代码。希望这能帮助你理解我在做什么