抽象的Bug们
抽象的BUG们
谨以此文章祭奠那些折磨我的抽象BUG
1.输入流混淆
在某年某月某日,舍友在开AcWing 4959这个题时,遇到了我可能一辈子不会遇到的BUG
我舍友的写算法习惯是在main函数里面套一个solve()来输出,这是他的写法
static void solve() throws IOException {
BufferedReader r=new BufferedReader(new InputStreamReader(System.in));
BufferedWriter w = new BufferedWriter(new OutputStreamWriter(System.out));
res = 0;
String[] s = r.readLine().split(" ");
n = Integer.valueOf(s[0]);
m = Integer.valueOf(s[1]);
for (int i = 1; i <= n; i++) {
String ss = r.readLine();
for (int j = 1; j <= m; j++) {
g[i][j] = ss.charAt(j - 1);
}
}
for (int i = 1; i <= n; i++) {
for (int j = 1; j <= m; j++) {
w.write(g[i][j]);
}
w.write("\n");
}
w.flush();
}
public static void main(String[] args) throws IOException {
BufferedReader r=new BufferedReader(new InputStreamReader(System.in));
T = Integer.valueOf(r.readLine());
while (T-- > 0) {
solve();
}
}
是不是完全没有问题?读取一个矩阵到数组里面再输出,然鹅却惨遭报错
Exception in thread "main" java.lang.NumberFormatException: For input string: ""
at java.base/java.lang.NumberFormatException.forInputString(NumberFormatException.java:67)
at java.base/java.lang.Integer.parseInt(Integer.java:675)
at java.base/java.lang.Integer.valueOf(Integer.java:992)
at DFS.solve(DFS.java:72)
at DFS.main(DFS.java:94)
即readline啥都没读到。于是我就开始了惨烈的debug之旅,在找了一个小时后,尝试了各种方法后,我直接新开了个类重新写读取方法,奇了,这次完美输入,什么错也没报,于是照葫芦画瓢填入,在反复比对中终于发现了问题
public static void main(String[] args) throws IOException {
BufferedReader r=new BufferedReader(new InputStreamReader(System.in));
T = Integer.valueOf(r.readLine());
while (T-- > 0) {
solve();
}
}
这么写必会报错,然鹅
public static void main(String[] args) throws IOException {
solve();
}
static void solve() throws IOException {
BufferedReader r=new BufferedReader(new InputStreamReader(System.in));
T=Integer.valueOf(r.readLine());
while (T-- > 0) {
…………//其他代码
}
这样却不会
chatgpt老师是这样说的
在每个测试用例中,您使用
r.readLine()来读取一行数据,但如果测试用例之间没有空行分隔,那么第一个r.readLine()在读取第一个测试用例的数据后,将指向第二个测试用例的数据行,这可能导致数据混淆。
将方法修改为
public static void main(String[] args) throws IOException {
BufferedReader r = new BufferedReader(new InputStreamReader(System.in));
int T = Integer.valueOf(r.readLine());
while (T-- > 0) {
solve(r);
}
}
static void solve(BufferedReader r) throws IOException {
String[] s = r.readLine().split(" ");
int n = Integer.valueOf(s[0]);
int m = Integer.valueOf(s[1]);
// 继续处理测试用例中的数据
// ...
// 注意:不再需要在 solve 方法中读取 T 的值
}
这样就对了
2.html固定748
在某天(大二寒假)愉悦写博客时,突然发现博文目录的sticky定位不起作用,顺藤摸瓜到父元素只有748,再顺藤摸瓜后发现整个html只有748,让人感慨。
于是在网上搜了一堆资料无果后使用终极手段——一个一个样式删的排除发,最终发现
当全局设置
设置html { height: 100%; }
会导致html的高度最大只有748,也就是一vw的高度,令人忍俊不禁,
是的,网上的教程在于说明如何占据一个全屏窗口,但是当你网页的高度大于全屏时记得取消掉这个
3.Spring的MapStructPlus无法进行Vo转换
记住,所有需要new的类要
@Autowired private Converter converter ;
尤其是这种需要动态依靠运行时生成的impl的
错因
private static Converter converter = new Converter();
“
4.Long自动拆箱
public static Long getTenantId() {
CustomUserDetails detail = DetailsHelper.getUserDetails();
return detail == null ? 0L : detail.getTenantId();
}
当detail不为null,但是detail.getTenantId()为null时会报空指针
原理
static Long get(){
return null ;
}
public static void main(String[] args) {
Long i = false?0L:get();
System.out.println(i);
}
在 return detail == null ? 0L : detail.getTenantId(); 这里,0L 是 基本类型 long,detail.getTenantId() 返回的是 包装类型 Long。
Java 需要让 两个返回值的类型保持一致,所以会自动将整个表达式的类型推断为 long,这就触发了 自动拆箱。然后 null → long 失败,抛出 NullPointerException。
==总结:三元表达式会触发自动拆箱==