我已经为我的项目启用了 Checkstyle。它在方法参数上显示黄色标记并请求将其设置为final。为什么?什么目的?如果不指定会出现什么问题?
我正在为我的Hangman游戏制作类似键盘的按钮(参见图片),我的问题是关于内部课程.我已经读过关于内部类的LINK,它说你只能用FINAL类型访问外部变量.但是如果我这样声明变量,我就不能再改变它的值......所以我的问题是我需要改变内部类中的值.我的代码如下:
public class MainGame extends JDialog {
private String player;
private char [] wordChar;
private JButton[] buttons;
private int level;
private int score;
private int livesLeft;
private int missedGuess;
void newGame() {
level = 0;
score = 0;
livesLeft = 10;
missedGuess = 0;
//label1:
// while (livesLeft!= 0) {
//get random WORD from LIST
Word hiddenWord = new Word();
//put random word in Array
wordChar = new char[hiddenWord.getHiddenWord().length()];
wordChar = hiddenWord.getHiddenWord().toCharArray();
buttons = …Run Code Online (Sandbox Code Playgroud) 如果我有这个匿名方法,我应该声明x变量为final.
private void testMethod (ListField<BeanModel> listField){
final ListLoader<BeanModel> loader = new PagedListLoader<BeanModel>();
listField.addListener(Events.Attach, new Listener<ListViewEvent<BeanModel>>() {
@Override
public void handleEvent(ListViewEvent<BeanModel> be) {
loader.load();
}
});
}
Run Code Online (Sandbox Code Playgroud)
但是,如果loader是一个类字段,则没有必要将其声明为final:
public class testClass{
private ListLoader<BeanModel> loader = new PagedListLoader<BeanModel>();
private void testMethod (ListField<BeanModel> listField){
listField.addListener(Events.Attach, new Listener<ListViewEvent<BeanModel>>() {
@Override
public void handleEvent(ListViewEvent<BeanModel> be) {
loader.load();
}
});
//Could I modify loader's reference here, before the method executes?
//loader = null;
}
}
Run Code Online (Sandbox Code Playgroud)
有没有人知道为什么他们保证局部变量在被访问时不会改变但是没有为类字段做?
在Java中,我有以下代码
List<Integer> myList = new ArrayList<>();
for (int i=0;i<9;i++) {
myList.add(i);
}
Integer sum = 0;
myList.forEach(i -> {
sum = sum + i; // does not compile, sum needs to be final or effectively final
});
for(int i : myList) {
sum = sum + i; //runs without problems
}
Run Code Online (Sandbox Code Playgroud)
我的问题是,为什么我不能在lambda中改变sum的值?它与下面的for循环完全相同,或者我错了?有趣的是,如果我将main方法之外的整数和声明为静态,它也可以.谁能解释我为什么?
编辑:在另一个类似的问题Java 8支持闭包,答案似乎是:
它是向后兼容性和项目资源约束的组合.
但是,我仍然无法理解为什么它可以工作,如果我将数组和数组或我在main之外声明它.我还想了解下面的myList.forEach和for循环之间有什么区别,为什么一个有效,另一个没有.
这个问题之前已经在这里被问过\n
\n我的问题为什么在这里得到回答\n
\n但是我对答案有一些疑问。\n提供的答案提到-
\n\n\n\n尽管其他答案证明了该要求,但它们没有解释该要求存在的原因。
\n
\n\nJLS 在\xc2\xa715.27.2中提到了原因:
\n
\n\n\n\n对有效最终变量的限制禁止访问动态更改的局部变量,捕获这些变量可能会引入并发问题。
\n
\n\n为了降低错误风险,他们决定确保捕获的变量永远不会发生变化。\n我对这会导致并发问题的说法感到困惑。\n
\n
我在Baeldung上阅读了有关并发问题的文章,但我仍然对它如何导致并发问题感到有点困惑,有人可以帮我举个例子吗。\n提前致谢。
\n我无法制作一个关闭此挥杆的按钮并返回上一个挥杆菜单.我试过以下......
btnBack = new JButton("Back");
btnBack.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
MainMenu gui = new MainMenu(uname);
gui.setVisible(true);
gui.pack();
gui.setLocationRelativeTo(null);
frame.setVisible(false);
frame.dispose();
}
});
Run Code Online (Sandbox Code Playgroud)
当我尝试这个时,它给了我错误
从内部类中访问局部变量框:需要声明为final
我修剪了我的代码删除我的JDBC
public class newImageViewer implements ActionListener {
JLabel lblInstru, lblInstruVal, lblInstrumentID, lblImgnameVal, lblImgtagVal, lblImgsizeVal, lblDateVal, lblImgpathVal, lblTakenbyVal, lblNoteVal, lblImgpath, lblTakenby, lblSalary, lblImgsize, lblDate, lblS,
lblSVal, lblNote, lblImgtag, lblImgname, imagel;
JTextField txtDate, txtImgpath, txtTakenby, txtImgname, txtImgtag, txtImgsize, txtNote, txtInstrumentID;
JButton btnAdd, btnUpdate, btnDelete, btnPrev, btnNext, btnBack;
ResultSet rs;
private ImageIcon image1;
String imagepath, uname; …Run Code Online (Sandbox Code Playgroud) 我想增加index每次迭代的值1.很容易实现for-loop.变量image是一个数组ImageView.
这是我的for-loop.
for (Map.Entry<String, Item> entry : map.entrySet()) {
image[index].setImage(entry.getValue().getImage());
index++;
}
Run Code Online (Sandbox Code Playgroud)
为了练习Stream,我尝试将其重写为Stream:
map.entrySet().stream()
.forEach(e -> item[index++].setImage(e.getValue().getImage()));
Run Code Online (Sandbox Code Playgroud)
导致我错误的原因:
错误:从lambda表达式引用的局部变量必须是final或者有效的final
如何重写Stream递增index要使用的变量?
我读这大约Lambda表达式梦幻般的文章,以下是未清除的对我说:
不要指望编译器捕获所有并发访问错误.禁止变异只适用于局部变量.
我不确定自我实验会涵盖所有情况,所以我正在寻找一个明确定义的规则:
不要指望编译器捕获所有并发访问错误.禁止变异只适用于局部变量.如果matches是封闭类的实例或静态变量,则不会报告错误,即使结果与未定义相同.
更新1:
自由变量 - 即不是参数且未在代码中定义的变量.
简单来说,我可以得出结论,自由变量是不是Lambda表达式参数的所有变量,并且没有在同一个Lambda表达式中定义?
此代码使用方法引用特定对象的实例方法:
public class Main {
public static void main(String[] args) {
One one=new One();
// F f = ()->{one.bar();}; //previous wrong syntax
F f = one::bar; //4
f.foo();
}
}
class One{void bar(){}}
interface F{void foo();}
Run Code Online (Sandbox Code Playgroud)
我知道它有效.但我无法理解为什么以及如何.
我无法理解的是,该F.foo()方法如何使用对不是方法本身的参数的对象的引用(签名不是void foo(One one)).
我在第4行
F接口的类的实例one对invoke bar()方法的引用来实现该方法但是如何才能foo()有one参考范围?我是否错误地试图将此解决方案转换为"传统的,明确的实现"?如果不是,那么"明确的对应物"是什么?
我正在研究Java 8流,我唯一的问题是了解lambda,这是为什么对于instance(和static)变量,lambdas中有效的最终警告会被忽略的原因。我似乎无法在网上找到任何提及它,因为大多数网页将刚才讲的是“有效决赛”的定义。
public class LambdaTest {
int instanceCounter = 0;
public void method() {
int localCounter = 0;
instanceCounter = 5; //Re-assign instance counter so it is no longer effectively final
Stream.of(1,2,3).forEach(elem -> instanceCounter++); //WHY DOES THE COMPILER NOT COMPLAIN HERE
Stream.of(1,2,3).forEach(elem -> localCounter++); //Does not compile because localCounter is not effectively final
}
}
Run Code Online (Sandbox Code Playgroud) java ×9
java-8 ×4
lambda ×4
final ×2
java-stream ×2
attributes ×1
checkstyle ×1
concurrency ×1
dictionary ×1
foreach ×1
swing ×1