大四开始找实习,被各种笔试、面试蹂躏,所以写一篇博客记录一下蹂躏我的那些题目,虽然它们对我百般摧残但我还是爱它们
1.byte类型,下面输出的是什么
byte b = 127;
b = b + 1;
System.out.println(b);
结果是编译不通过;
原因在于因为b为变量,java编译无法确定b+1是否会超过(byte的范围[-128,127]),所以编译无法通过;
那如果b=1+2呢?答案是全部正常,因为1跟2都是常量,编译能确定b不会超过(byte的范围[-128,127])
借此机会延伸一下:
byte b=127;
b++;
System.out.println(b);
答案是-128,接下来我们就来看看为什么:
- 首先我们知道计算机是以二进制的形式存储数据的
- 机器数:首位数(符号位)0表示正数,1表示负数
- 在计算机中,正数是直接用原码表示的,负数用补码表示
- 正数的原码、反码、补码相同
- 负数的反码为:除符号位外,原码各位取反,得负数的反码;
- 负数的补码为:反码+1就是补码。
- 补码反算原码:符号位不变(即1),其余各位取反后加1,与原码算补码一样
原码:将一个整数,转换成二进制,就是其原码。如单字节的5的原码为:0000 0101;-5的原码为1000 0101。
ok,也会是说127二进制是01111111,加1后为10000000,符号位1为负数,即补码形式存储,转为原码为11111111+1即真值10000000又为负数所以-128;当在一个i++;后为多少呢,我就不说了,你们可以试一下
再延伸:
int b = 389;
byte i = (byte)b;
System.out.println(i);
答案是-123,首先int是4字节32位,二进位即为00000000 00000000 00000001 10000101,byte一个字节,所以得到的结果是10000101,为负数且以补码形式存储,得到原码为11111010+1为11111011即-127+4=-123
关于byte就这样
2.final关键字
- final修饰的类不能被继承
- final修饰的方法不能被子类重写
- final修饰的变量是常量,只能被赋值一次,且不会被初始化(很好理解),调用之前需要先赋值,不然会编译错误;
3.类的继承,抽象类以及接口
- 一个类只能有一个直接父类,但可以实现多个接口,用逗号隔开;但如果该类是一个接口,它可以通过extends继承多个接口,记住是接口;
- 类class,抽象类abstract,接口interface
- 抽象类不能被实例化。抽象方法必须用abstract修饰,且包含抽象方法的类必须声明为抽象类,但抽象类可以不包含抽象方法;
- 接口不能被实例化,接口的所有方法都是抽象方法,而且默认使用public abstract来修饰,而所有变量默认使用public static final来修饰,即公共静态常量;
- 抽象类跟接口的区别:
1.抽象类要被子类继承,接口要被类实现。
2.接口只能做方法声明,抽象类中可以作方法声明,也可以做方法实现。
3.接口里定义的变量只能是公共的静态的常量,抽象类中的变量是普通变量。
4.抽象类可以有具体的方法和属性,接口只能有抽象方法和不可变常量。
5.接口是设计的结果,抽象类是重构的结果。
6.一个类只能继承一个抽象类,但可以实现多个接口;
4.String,SringBuilder,StringBuffer之间的关系以及区别
参考:https://blog.csdn.net/yajing8/article/details/73695170
再一点:
下面两天语句的区别:
String name = "abc";
String name = new String("abc");
前提:这两条语句是独立分开的完全没关系的;
String name = "";只创建一个对象:会创建一个字符串常量abc放入字符串常量池,然后name引用指向这个常量内存地址;
String name = new String("");创建两个对象:会创建一个字符串常量放入字符串常量池,然后再创建一个String对象放入堆,引用name指向这个对象,对象又指向常量池的abc;
再说一个:String a="ab"+"cd";会被优化成String a="abcd";
5.关于try,catch,finally执行顺序以及return语句的执行情况
参考:https://blog.csdn.net/yajing8/article/details/73695170
6.关于表单重复提交产生的原因以及解决方法
产生的原因:
- 用户重复点击提交
- 提交 form 表单,后端未返回结果(还在处理请求)时,刷新页面
- 后端已处理返回结果,用户后退
解决的方法:
- 前端解决:
1.将提交按钮锁定
2.ajax方式,不存在刷新再次提交问题
3.ajax方式,不存在返回再次提交问题 - 后端解决:
使用session解决:
第一步:首先后端生成一个token存入session,放入前端的隐藏域,提交表单时一同提交上去
第二步:读取前端提交的toke和session的token判断是否相等,相等就是第一次提交,否则就是重复提交
第三步:自己的业务逻辑处理
第四步:成功就移除session的token
7.SQL
- 使用
limit m offset n
分页时,可简写为limit m,n;m表示每页最多的数据条数,随着N
越来越大,查询效率也会越来越低。 - 聚合查询:
COUNT(*)
和COUNT(id)
实际上是一样的效果。另外注意,聚合查询同样可以使用WHERE
条件,因此我们可以方便地统计出有多少男生、多少女生 - 查找有重复的数据,关键字group by以及having count(重复的列)>1:
select * from test where name in (select name from test group by name having count(name) > 1);
- 查找去重,关键字distinct:
select distinct name from test
关于distinct:
- 只能过滤掉重复数据,并返回该字段所有符合where的数据,无法返回其他字段
- 如果是distinct name,id 这样的mysql 会认为要过滤掉name和id两个字段都重复的记录
- 如果sql这样写:select id,distinct name from user,这样mysql会报错,因为distinct必须放在要查询字段的开头。
- 所以一般distinct用来查询不重复记录的条数:select count(distinct name) from test;
- 如果要查询不重复的记录,有时候可以用group by :select id,name from test group by name;
8.for的运行步骤
class Demo{
public static void main(String[] args){
int x = 1;
for(show('a'); show('b') && x<3;show('c')){
show('d');
x++;
}
}
public static boolean show(char ch){
System.out.print(ch);
return true;
}
}
运行结果为:abdcbdcb
第一次循环:a b d c
- 首先运行for初始化代码块,即show('a');
- 运行判断语句:show('b') && x<3;
- 运行show('d');x++;
- 运行show('c');
第二次循环:b d c
- 不会再运行初始化代码,直接运行判断语句:show('b') && x<3;
- 运行show('d');x++;
- 运行show('c');
第三次循环:b
- 直接运行判断语句:show('b') && x<3; 此时x=3;不满足循环条件,循环结束
如果循环田间语句为x<3&&show('b') ;第三次循环结果还是abdcbdcb吗?
9.new一个对象发生了什么
https://www.cnblogs.com/JackPn/p/9386182.html