1. 聚能聊>
  2. 话题详情

Java开发者们,那些年我们一起踩过的坑

lpajwtbt_2
  
阿里大法 《阿里巴巴Java开发手册(正式版)》发布! 当然好的规范在一定程度上可以避免一些坑。

然而在实际开发中,由于开发者水平不同,写出的代码质量也有所迥异。

我们每天都在写Java程序,可能我们更多的是为了结果,但是在写代码的过程中还是有许多需要注意的地方。
  
一些初级开发者甚至老手为了方便可能会在Spring中的Service中添加成员变量,由于Spring的bean默认是单例模式,对于单例模式来说,不仅方便多线程调用该实例,更主要是减小了频繁创建带来的系统消耗。然而在多线程下并发会导致数据混乱。
  
最容易被忽视的Integer数据类型比较,使用==比较 而得到与期望相反的结果。

Integer a = 128;
Integer b = 128;
System.out.println(a==b);

  

HashMap size陷阱,本意是希望给HashMap设置初始值, 避免扩容(resize)的开销,但没有考虑当添加的元素数量达到HashMap容量的75%时将出现resize。

Map map = new HashMap(collection.size());  
for (Object o : collection) {  
      map.put(o.key, o.value);  
}

  
不使用finally块释放资源,导致一直占用内存。

多年的开发后,多多少少大家都会有经历过各式各样的暗坑,只有这样才会促使开发者成长。大家又有踩过那些"暗"坑呢?筒子们都来聊聊,彼此长长经验。

参与话题

奖品区域 活动规则 已 结束

  • 奖品一

    淘公仔 x 3

  • 奖品二

    聆听专属T恤衫 x 3

  • 奖品三

    淘公仔U盘 x 2

66个回答

1

张维-IT&阿里云 复制链接去分享

坑多的都没有地方存了。 哎。。

package day02;
/**

  • 1:java初学习,避免面试时一些HR挖的坑。
  • @author biexiansheng
    *

*/
public class Test02 {

public static void main(String[] args) {
    // ctrl+shift+f自動排版
    int a=120;
    byte b=9;
    b=(byte)(a+b);//需要强制类型转换
    System.out.println("b="+b);
    
    System.out.println('a'+1);
    System.out.println('A'+1);
    System.out.println("hello"+'a'+1);
    //任何数据类型加字符串等于字符串
    System.out.println('a'+1+"hello");
    System.out.println("hello"+1+'a');
    
}

}

运行结果:

b=-127
98
66
helloa1
98hello
hello1a

package day02;

/**

  • 1:java初学习,避免面试时一些HR挖的坑。
  • @author biexiansheng
    *

*/
public class Test02 {

public static void main(String[] args) {
    // ctrl+shift+f自動排版
    //b1,b2时两个变量,变量里面存储的值都是变化的,所以在程序运行中jvm是无法判断里面具体的值
    //byte类型的变量在进行运算的时候,会自动转换为int类型
    byte b1=3;
    byte b2=4;                    //'0'--48 'a'--97 'A'--65
    //byte b3=b1+b2;报错    
    //byte b3=(byte)(b1+b2);ok
    byte b4=3+4;
    //byte short char ->int->long

    

}

}

package day02;

/**

  • 1:java初学习,避免面试时一些HR挖的坑。
  • @author biexiansheng
    *

*/
public class Test02 {

public static void main(String[] args) {
    // ctrl+shift+f自動排版
    System.out.println(10/3);
    System.out.println(10/3.0);
    System.out.println(10*3.0);
    System.out.println("3+4="+3+4);
    //+号代表第一加号,第二连接,第三代表正数。
    int a=3;
    System.out.println("a++="+(a++));//先输出再++
    System.out.println("a="+a);//输出上面的++后面的值
    System.out.println("++a="+(++a));
    int b=3;
    int c;
    c=b++;//后++,先使用再++
    //c=++b;先++,先++后使用
    System.out.println("b="+b);
    System.out.println("c="+c);
    
    
}

}

package day02;

/**

  • 1:java初学习,避免面试时一些HR挖的坑。
  • @author biexiansheng
    *

*/
public class Test02 {

public static void main(String[] args) {
    // ctrl+shift+f自動排版
    int a = 4;
    int b =(a++)+(++a)+(a+10);
    //a 5 6  
    //b 4+6+6+10
    System.out.println("a="+a);
    System.out.println("b="+b);
    
    
    int c = 4;
    int d = (--c)+(c--)+(c*10);
    //c 3 2
    //d 3+3+20
    System.out.println("c="+c);
    System.out.println("d="+d);
    
    
}

}

答案:

a=6
b=26
c=2
d=26

package day02;

/**

  • 1:java初学习,避免面试时一些HR挖的坑。
  • @author biexiansheng
    *

*/
public class Test02 {

public static void main(String[] args) {
    // ctrl+shift+f自動排版
    byte a=3;
    a++;
    System.out.println("a="+a);//先使用再++
    //System.out.println("a++="+(a++));
    a=(byte)(a+1);//byte类型自动转换为int类型的,所以需要强制转换一下。
    System.out.println("a="+a);
    
    short s=1;
    s=(short)(s+1);
    short s1=2;//这是坑,面试的坑
    s1+=1;//<==>s1=(short)(s1+1);
    
}

}

package day02;

/**

  • 1:java初学习,避免面试时一些HR挖的坑。
  • @author biexiansheng
    *

*/
public class Test02 {

public static void main(String[] args) {
    // ctrl+shift+f自動排版
    int a=10;
    int b=20;
    int c=30;
    System.out.println(a>b & a>c);//false false flase
    System.out.println(a<b & a<c);//true true ture
    System.out.println(a<b & a>c);//true false false
    System.out.println(a>b & a<c);//false true flase
    System.out.println("------------");
    System.out.println(a>b | a>c);//false false false
    System.out.println(a<b | a<c);//true true true
    System.out.println(a>b | a<c);//false true true
    System.out.println(a<b | a>c);//true false true
    System.out.println("----------");
    //相同为false,不同为true;逻辑异或
    System.out.println(a>b ^ a>c);//false false false
    System.out.println(a<b ^ a<c);//true true ture
    System.out.println(a>b ^ a<c);//false true true
    System.out.println(a<b ^ a>c);//true false true
    System.out.println("------------");
    System.out.println(!true);
    System.out.println(!!true);
    
    
}

}

package day02;

/**

  • 1:java初学习,避免面试时一些HR挖的坑。
  • @author biexiansheng
    *

*/
public class Test02 {

public static void main(String[] args) {
    // ctrl+shift+f自動排版
    //短路与&&,前错后不执行
    //短路或||,前对后不执行
    int x=3;
    int y=4;
    //System.out.println((x++)==3 && (++y==4));//前对后执行
    //System.out.println((x++)==3 & (++y==4));//前对后执行
    //System.out.println((++x)==3 && (++y==4));//前错后不执行
    System.out.println((++x)==3 & (++y==4));//前错后不执行
    System.out.println("x="+x);
    System.out.println("y="+y);
    
}

}

package day02;
import java.util.Scanner;
/**

  • 1:java初学习,避免面试时一些HR挖的坑。
  • @author biexiansheng
    *

*/
public class Test02 {

public static void main(String[] args) {
    Scanner s=new Scanner(System.in);
    System.out.println("请输入三个数值a:");
    int a=s.nextInt();
    System.out.println("请输入三个数值b:");
    int b=s.nextInt();
    if(a==b){
        System.out.println("a和b相等哟!");
    }else{
        System.out.println("a和b的值不相等哟!");
    }
    System.out.println("--------------------");
    int num=a<b? a:b;
    System.out.println("a,b两个数之间的最小值:"+num);
    System.out.println("--------------------");
    System.out.println("请输入三个数值c:");
    int c=s.nextInt();
    /*int min=a<b? a:b;
    int min2=min<c? min:c;
    System.out.println("a,b,c三个数的最小值:"+min2);*/
    int min=a<b? (a<c? a:c):(b<c? b:c);
    System.out.println("a,b,c三个数的最小值:"+min);
    
}

}

1

holyware 复制链接去分享

JAVA内存泄露问题
1、监听器
在java 编程中,我们都需要和监听器打交道,通常一个应用当中会用到很多监听器,我们会调用一个控件的诸如addXXXListener()等方法来增加监听器,但往往在释放对象的时候却没有记住去删除这些监听器,从而增加了内存泄漏的机会。
2、各种连接
比如数据库连接(dataSourse.getConnection()),网络连接(socket)和io连接,除非其显式的调用了其close()方法将其连接关闭,否则是不会自动被GC 回收的。对于Resultset 和Statement 对象可以不进行显式回收,但Connection 一定要显式回收,因为Connection 在任何时候都无法自动回收,而Connection一旦回收,Resultset 和Statement 对象就会立即为NULL。但是如果使用连接池,情况就不一样了,除了要显式地关闭连接,还必须显式地关闭Resultset Statement 对象(关闭其中一个,另外一个也会关闭),否则就会造成大量的Statement 对象无法释放,从而引起内存泄漏。这种情况下一般都会在try里面去的连接,在finally里面释放连接。

0

1582870284259721 复制链接去分享

我遇到最奇怪的就是一个正则表达式的声明,没有使用static,结果在线上把整个服务器集群cpu全部跑满;由于该正则并非时刻都被调用,本地测试又不能重现,运维同学都差点哭了,后台把虚拟机堆栈拖出来,才发现该问题,此后我对正则的敬畏之心又多了三分......我要云栖的T恤,😄

hzaaaa 回复

请进

评论
0

李四爷 复制链接去分享

每个程序员的开发都在用心去写程序 日夜辛苦值得赞赏 我想要一个U盘.

聚小编 回复

U盘也是要靠努力才能获得呀~看看获奖的高手们是肿么写的,学习一下~

评论
0

孤尽 复制链接去分享

《阿里巴巴Java手册》中,以实际案例出发,以Java开发者为中心视角,来决定是否留用此条规则。Java语言本身并没有太多这样那样的漏洞,一切是与场景有关,与错误的理解有关,阿里是一家大公司,有着近万人的开发人员,难以保证每个人对于知识点的认识与运用都是一样的,我们精心筛选了很多案例,总结成册,希望帮助到大家;至于为什么要有数据库、安全、日志,这是与Java工程师悉悉相关的知识点,比如,数据结构的考量不一样,那么上层代码的实现就非常痛苦。最简单地说,对于是与否,公司里有三套做法:1/0,Y/N,true/false,这样导致上层应用经常踩坑,沟通成本增加。本手册已经更新至1.0.2版本,修正了第一版的近15个问题,我们以虚心的态度,开放的心态与大家一起快乐工作,轻松生活。

聚小编 回复

来帮你上个链接,《阿里巴巴JAVA手册》下载入口https://yq.aliyun.com/articles/69327

评论
0

millerwanglei 复制链接去分享

说多了都是泪

0

ianly 复制链接去分享

评论很精彩

0

c1040473977 复制链接去分享

踩着别人走过坑,自己的摸爬滚打,从不懂到懂,从不规范到规范。

0

小悦悦儿 复制链接去分享

0

1843588941075393 复制链接去分享

好想认真学习一下,可是总没有时间,还是谢谢

0

tineye 复制链接去分享

11

0

1507488927378677 复制链接去分享

哈哈,打个酱油

0

1954988880158386 复制链接去分享

很早就接触过java,最初是txt,后来是游戏。

0

1756288792519043 复制链接去分享

对啊

0

1322988895943130 复制链接去分享

23333

0

1200988879711845 复制链接去分享

你好

0

1678788880045055 复制链接去分享

不太清楚,来看看

0

1089455678362915 复制链接去分享

试试

0

1291788874573609 复制链接去分享

哈哈

0

有众逐虎 复制链接去分享

表示从入门到跑路了我

4