alt+enter:自动补全
ctrl+d:复制当前内容到下一行
ctrl+f5:程序再运行一次
100.for:自动生成循环一百次的for循环语句
数组名.fori:自动生成正着循环遍历数组的语句
数组名.forr:自动生成倒着循环遍历数组的语句
fori+tab键:自动生成for循环
alt+insert:自动生成类中常用的方法
ctrl+h:显示继承树
ctrl+i:快速生成抽象方法的实现
ctrl+alt+T:可以选择自动生成try、catch、finally代码块
ctrl+alt+L:自动格式化代码
ctrl+p:查看方法需要的参数
ctrl+alt+M:选中代码段,可以自动抽取方法
shift+f6:变量的批量修改,先选中要修改的内容,再按组合键,修改时下面相同内容也会跟着做出相应修改
按住鼠标滚轮不松,可以竖着选中,或者按住alt不松,用鼠标左键选中
插件PTG:安装后可以右键点击ptg to JavaBean,直接生成标准的JavaBean
ctrl+alt+v:自动生成定义变量的左边代码
ctrl+b:跳转到源码
ctrl+alt+t:选中代码块,按组合键可以选择相应的语句将代码块包裹起来
ctrl+n:搜索
ctrl+shift+u:全部变为大写
Java中有三种注释:
*@Description Hello
*@Author ***
*/
其中@是描述符
Java是一门强类型语言,即变量的使用要严格符合规定,所有变量要先定义后才能使用
Java数据类型分为两大类,基本类型和引用类型
整数类型
long a=30L;//long类型后面要加个L
整数类型拓展:
二进制0b;八进制0;十六进制0x
//不同进制赋值
int i = 10;
int i1 = 010;//八进制
int i2 = 0x10;//十六进制赋值
浮点类型
float a=50.1F;//float类型后面要加个F
浮点数拓展:
//float和double类型的两个值相同的数,他们的比较结果的布尔值是false
float a = 0.1;
double b = 1.0/10;
//变量a和b的比较结果是false
//因此银行业务中,表示钱不用float或者double,而是用BigDecimal(数学工具类)表示
字符类型
字符拓展:
//字符在内存中存放的都是相应字符的数值,ASCII码或者Unicode码(表示方式:'\u0061')
boolean类型:占一位,只有true和false两种
类、接口、数组
低------------------------------------------------------------------------>高
byte,short,char->int->long->float->double
double a = 1.5;
int b = (int)a;//此时b为1
注意:
Java变量是程序中最基本的存储单元,包括变量名,变量类型和作用域。
type varname [=value][{,varname[=value]}];
//数据类型 变量名 = 值;可以用逗号隔开来声明多个同类型变量
变量命名要满足命名规则:字母、下划线、$开头,不能用标识符命名
public class Variable{
static int allClicks=0; //类变量
int age;
String name;
//如果不进行初始化会有默认值,int的默认值为0,String的默认值为null
String str = "hello world";
public void method(){
int i = 0; //局部变量
}
}
常量:初始化之后就不能再改变的值
final 常量名 = 值;(常量名一般为大写字符)
final PI = 3.1415926;
int a = 1;
int b = a++;//表示先把a的值赋给b,然后a再加一
/* 等同于
int b =a;
a = a+1;
*/
int c = ++a;//表示的a的值先加1,然后再把a的值赋给c
/* 等同于
a = a+1;
int c = a;
*/
注:该类运算符中存在一种短路现象,即如果运算符左边的值就已经能决定该表达式的值了,那么就不再计算该运算符右边的表达式了。
int c = 5;
boolean d = (c<4)&&(c++<4);
System.out.println(d);//输出false
System.out.println(c);
//输出5,表示并没有执行(c++<4)这个表达式,因为逻辑运算符左边的表达式已经可以决定整个表达式的值了
^为异或
移位运算符的效率很高,因此有时可以通过以为操作来实现乘方运算,左移一位相当于乘2,右移一位相当于除2
表达式1?表达式2 :表达式3
表示如果表达式1的值为真,那么整个表达式的值为表达式2的值,否则为表达式3的值
+=、-+、*=、/=、%=这些运算符在参与运算时,编译器都会自动加上一个强制类型转换,相当于:
short a = 1;
short b = 2;
a += b;//相当于a = (short)(a+b);
//因为short、byte、char类型相互参与运算时,都会先提升为int类型
//语法格式
package pkg1.[pkg2[.pkg3..];//必须写在程序的最开头
/*包的命名格式一般是公司域名倒置
如:com.baidu
*/
//导入要使用的包
import package pkg1.[pkg2[.pkg3..];
javadoc是用来生成api文档的,需要在程序中写好文档注释
在命令行执行:javac 参数 程序文件名称
javadoc -encoding UTF-8 -charset UTF-8 Doc.java
#-encoding UTF-8 -charset UTF-8为参数,使中文字体可以展示出来
/**
*@author xxx
*version 1.0
*since 1.5
*/
public class Doc{
String name;
/**
*@author xxx
*@param name
*@return
*/
public String test(String name){
return name;
}
}
在idea中生成api文档的方法:
接下来在底部的Locale输入框配置语言和编码集,语言用zh_CN,代表中文,其他的输出和控制塔一致
注意:生成的文档里面会有很多 .html 文件 正常
Java提供了一个工具类,用来获取用户的输入。java.util.Scanner
基本语法:
Scanner s = new Scanner(System.in);
s.close(); //用完关闭
通过Scanner类的next()和nextline()方法获取输入的字符串,在读取钱一般要使用hasNext()与hasNextline()判断是否还有输入的数据。
next():
nextline():
类似还有输入整数或者其他类型的方法,如
nextInt()、nextFloat()
程序按顺序依次执行
if语句:
if(表达式){
//如果表达式为true要执行的语句
}else if(){
//反之执行的语句
}.....
switch语句:
switch case语句判断一个变量与一系列值中某个值是否相等,每个值为一个分支
switch(expression){
case value:
//语句
break;//可选,用来表示结束
case value:
//语句
break;//可选
//可以有任意数量的case语句
default://可选,都不满足时执行的语句
//语句
}//括号也表示结束
switch语句中的变量类型可以是:
注:
在switch结构中的case分支下要写break语句,如果表达式与case分支的标签相匹配,但是该case分支里没有break语句,那么程序会顺序执行后面的case分支,直到遇到break语句或者到达default分支,或者遇到“}”才结束。
jdk12的新特性:
书写switch结构的格式有变化
int number = 1;
switch(number){
case 1 ->{
}
case 2 ->{
}
case 3 ->{
}
default ->{
}
}
/*
这种格式可以省略书写break语句,用{}代替了,不会出现case穿透的现象,并且case后面的语句如果只有一句,那么大括号也可以省略。
*/
int number = 1;
switch(number){
case 1 -> System.out.println("一");//只有一句
case 2 ->
case 3 ->
default ->
}
/*如果switch语句中的内容想要赋值给某个变量,也可以简化代码*/
String str = switch(number){
case '0' -> "";
case '1' -> "一";
default -> "";
};
while循环:
while(表达式){
//循环语句
}
//表达式为真时一直循环下去
do while循环:
do{
//循环语句
}while(布尔表达式)
while和do while的区别:
- while先判断后执行,do while先执行后判断
- do while至少被执行一次
for循环:
for(初始化;布尔表达式;更新){
//循环语句
}
//不写布尔表达式,默认为真,也就是死循环
增强for循环:
主要用于数组或集合的遍历
for(声明语句 : 表达式){
//代码语句
}
//例
int[] nums = {1,2,3,4,5};
for(int x:nums){
System.out.println(x);
}
注:
声明语句:声明新的局部变量,该变量的类型必须和数组类型匹配。其作用域限定在循环语句块,其值与此时数组元素的值相等。
表达式:表达式是要访问的数组名,或者是返回值维数组的方法。
Random类
用来生成随机数,如:
import java.util.Random;
Random r = new Random();
int number = r.nextInt(100);//表示生成0--99之间的任意的一个随机数,包头不包尾,包左不包右
break用于强行退出循环,不执行循环中剩余的语句
continue语句,用于终止本次循环,接着执行下一次循环
break outer:中断当前循环并跳出标签所指的循环
continue outer:重新跳到标签的位置,并开始标签之后声明的循环
使用带标签的 break / continue 的原因是:为了跳出或重新开始多层嵌套循环。
Java方法是语句的集合,它们在一起执行一个功能。
方法包含一个方法头和方法体:
修饰符 返回值类型 方法名(参数类型 参数名,参数类型 参数名,...,...){
...
方法体
...
return 返回值;
}
方法调用:
调用方法:对象名.方法名(实参列表)
Java支持两种调用方法的方式,根据方法是否返回值来选择
int a = max(30,40);
System.out.println("Hello World");
注:Java中都是值传递,没有引用传递
如果希望在运行程序时给程序传递消息,需要考传递命令行参数给main()函数实现。
public class Demo{
public static void main(String[] args){
for(int i = 0; i < 10; i++){
System.out.println("args["+ i +"]:" + args[i] );
}
}
}
public static void printMax(double... numbers){
if(numbers.length == 0){
System.out.println("No argument passed!")
rutrun;
}
double result = numbers[0];
for(int i=1; i<numbers.length; i++){
if(numbers[i]>result){
result = numbers[i];
}
}
System.out.println("This max value is " + result);
}
声明数组的语法
dataType[] arrayRefVar;//首选的方式
dataType arrayRefVar[];//效果相同,但不是首选方式
用new操作符来创建数组:
dataType[] arrayRefVar = new dataType[arraySize];
数组元素是通过索引访问的,数组索引从0开始
获取数组长度:arrays.length
声明在栈区,实例在堆区
int[] a = new int[]{1,2,3};//静态初始化的完整格式
int[] a = {1,2,3};
Man[] mans = {new Man(1,1),new Man(2,2)};
int[] a = new int[2];
a[0] = 1;
a[1] = 2;
数组是引用类型,他的元素相当于累的实例变量,因此数组一经分配空间,其中的每个元素也被按照实例变量的方式被隐式初始化
public class HelloWorld {
public static void main(String[] args) {
double[] array = new double[]{1.1,2.2};
System.out.println(array);//[D@1b6d3586
}
}
/*
[D@1b6d3586的含义
[:代表是一个数组
D:代表数组的类型是double
@:分隔符(固定格式)
1b6d3586:数组真正的地址,十六进制的
*/
动态初始化:手动指定数组长度,由系统给出默认初始化值
静态初始化:手动指定数组元素,系统会根据元素个数,计算出数组的长度
数组的大小是固定的,因此超过数组的大小会报错
ArrayIndexOutOfBoundsException:数组下标越界异常
多维数组可以看成是数组的数组,比如二维数组就是一个特殊的一维数组,其中的每个元素都是一个一维数组
int a[][] = new int[2][5];//数组a可以看成是一个2行5列的矩阵
面向过程:按步骤一步一步的去完成,适合处理较为简单的问题
面向对象:将特点类似的众多对象归为一类,从而产生多个类,然后再对这些类下面的细节进行面向过程的分析,适合多人协作的复杂问题。
面向对象编程(Object-Oriented Programming,OOP)
面向对象三大特征:封装、继承、多态
类是一种抽象数据类型,是对某一类事物的整体描述,并不代表一个具体的事物。
对象就是类的一个具体实例。
Person p = new Person();//此时变量p就指向了一个Person类型的实例
构造方法是在创建对象时必须要调用的,可以在构造方法中写初始化信息,且其有两个特点:
无参构造方法:
没有参数的构造方法,在创建类时如果不主动编写,编译器会自动为该类生成一个无参构造方法。
public class Person{
String name;
public Person(){
//无参构造方法
}
}
有参构造方法:
带参数的构造方法,如过在类中编写,则需要显式的写出无参构造方法,否则会报错。
public class Person{
String name;
public Person(){
//无参构造方法
}
public Person(String name){//有参构造方法
this.name = name;
}
}
开发程序要求高内聚低耦合,因此需要封装,将更多的信息隐藏起来,不需要暴露给用户。
例如使用get()/set()方法来操作类中的属性
public class Student{
private String name;//私有属性不能用对象来直接访问
public String getName(){//通过公有属性的get方法来获得私有属性的值
return this.name;
}
public void setName(name){//通过公有属性的set方法来设置私有属性的值
this.name = name;
}
}
对象代表什么,就得封装对应的数据,并提供数据对应的行为
一个类可以通过继承另一个类,来获得另一个类的公有和保护属性的方法和属性,通过extends关键字表示,这连个类一个称为父类,一个称为子类
public class Person{
public String name;
protected int age;
private char sex;
}
public class Student extends Person{
public int id;
}
//在main方法中
Student s = new Student();
/*
此时对象s只能访问父类Person中的公有和保护的属性和方法,不能访问父类以及自身类中的私有的属性和方法
*/
Java中只有单继承没有多继承,但是java中有接口,一个类可以实现多个接口,相当于变相的实现了多继承
super代表父类,类似于this代表当前的对象
public class Person{
private String name;
public Person(){
System.out.println("Person");
}
public void say(){
System.out.println("说了一句话");
}
}
public class Student extends Person{
public Student(){
System.out.println("Student");
super.say();//在子类中使用super关键字调用父类的方法
}
}
//在main方法中
Student s = new Student();
/*
创建完对象之后,会按顺序输出
Person
Student
说了一句话
因此可以得出结论,在创建子类对象时,编译器会自动在子类的无参构造方法中的最开始调用父类的无参构造方法,即在子类的无参构造方法中不主动去调用父类的无参构造方法,编译器也会自动去完成;但是:如果显式的在子类的无参构造方法中调用父类的构造方法,必须要写在子类构造方法的第一行,如
public class Student extends Person{
public Student(){
super();//调用父类的构造方法
System.out.println("Student");
super.say();//在子类中使用super关键字调用父类的方法
}
}
*/
super注意点:
1. super调用父类的构造方法时只能在本类构造方法的第一行
1. super只能出现在子类的方法或者构造方法中
1. super和this不能同时调用构造方法,因为这两个都要求在构造方法的第一行
和this的区别:
代表的对象不同
this:当前对象
super:父类对象的引用
2.前提
this:没有继承也能使用
super:只能在继承条件下才能用
3.构造方法
this():本类的构造方法
super():父类的构造方法
子类可以对父类中方法的实现进行重新编写,但是子类方法的名字、类型、返回值类型、参数列表都要和父类的方法相同
public calss A{
public static void test(){
System.out.println("A->test");
}
}
public calss B extends A{
public static void test(){
System.out.println("B->test");
}
}
//main方法里
A a = new B();//父类的引用可以指向子类
a.test();
B b = new B();
b.test();
/*
输出
A->test
B->test
结论:虽然在子类中对父类中的test方法进行了重新编写,但是这个test方法是静态方法,静态方法在类加载时就已经创建了,因此当用对象实例去调用时,调用的还是当前对象所在类中的方法
*/
public calss A{
public void test(){
System.out.println("A->test");
}
}
public calss B extends A{
public void test(){
System.out.println("B->test");
}
}
//main方法里
A a = new B();//父类的引用可以指向子类
a.test();
B b = new B();
b.test();
/*
输出
B->test
B->test
结论:在子类中对父类中的test方法进行了重新编写,但是创建的对象实例是子类的类型,因此在调用时只会调用子类中已经重写了的方法
*/
重写:需要有继承关系,在子类中重新编写父类的方法!
1. 方法名必须相同
1. 参数列表必须相同
1. 修饰符:范围可以扩大,但是不能缩小;public>protected>default>private
1. 抛出异常,范围可以缩小但是不能扩大;
为什么要重写?
public class Perrson{
public void say(){
System.out.println("person");
}
}
public class Student extends Perrson{
public void say(){
System.out.println("student");
}
public void eat(){}
}
//在main方法里
//父类可以指向子类的对象,多态的表现
Student S1 = new Student();
Person S2 = new Student();
Object S3 = new Student();
s1.say();
s2.say();
/*
输出结果:
student
student
*/
s1.eat();
/*s2.eat();会报错,因为S2是Person类型的引用,在Person类中并没有eat方法,因此需要把Person类型的引用转换成Student类型才能使用eat方法,如 */
((Student) S2).eat();
/*
结论:对于父类和子类中都有的方法,实例对象最后会调用子类中重写的方法,如果是子类中有的而父类中没有的方法,那么父类类型的引用无法调用,需要强置类型转换之后才能调用
*/
instanceof关键字可以判断某个类型的引用是否指向某个具体类型的对象
规则:父类可以指向子类
//Student Teacher 都是Person的子类
Objcet object = new Student();
System.out.println(object instanceof Student);//true
System.out.println(object instanceof Person);//true
System.out.println(object instanceof Object);//true
System.out.println(object instanceof Teacher);//false
System.out.println(object instanceof String);//false
子类可以直接转换成父类类型,父类类型需要强制类型转换成子类类型
使用printf打印输出时,可以使用占位符,如:
System.out.printf("%s你好啊","张三");//输出:张三你好啊
被static关键字修饰的属性或方法都是静态的,这种属性和方法都属于静态的,被存放到静态内存区,并并不属于任何一个对象,它是属于整个类的,当类被加载时,这些静态方法和属性就被创建了,因此可以通过类名来调用这些方法,而非静态方法就不可以,因此非静态方法在没有创建对象的时候是不存在的,同样在编写类中方法时,在静态方法中也不能调用非静态方法和属性,因为在创建静态方法的时候,非静态方法还不存在,也就无法在静态方法中调用了。
public class Person{
{
//局部代码块,用来赋初始值
//变量只能在这里面使用,用完就释放了
System.out.println("匿名代码块");
}
static {
//静态代码块,类加载时就存在了,只执行一次
System.out.println("静态代码块");
}
public Person(){
System.out.println("构造方法");
}
}
//mian方法中
Person p = new Person();
/*
输出结果:
静态代码块
匿名代码块
构造方法
结论:
创建对象时,先加载静态代码块,然后是匿名代码块,最后是静态方法
*/
import static java.lang.Math.random;
import static java.lang.Math.PI;
public abstract calss Person{//抽象类
public void run(){}
public abstract void say();//抽象方法
}
注:抽象类虽然不能实例化对象,但是它也可以有构造方法构造方法的作用有两个,一个是初始化变量,另外一个是实例化对象,抽象类不能实例化,还可以做另外一个作用。
接口:只有方法的定义,没有方法的实现,关键字interface
public interface UserServices{
[public static final] int AGE = 10;
[public abstract ]void run(String name);
void insert(String name);
void delete(String name);
void update(String name);
void query(String name);
}
接口都有实现类,关键字为implements;(一个类可以实现多个接口),实现类中必须实现接口中的全部方法
public class UserServicesImpl implements UserServices{
public void insert(String name){}
public void delete(String name){}
public void update(String name){}
public void query(String name){}
}
接口和接口之间可以单继承,也可以多继承,当实现已经继承父接口的子接口时,需要重写父接口和子接口中的所有抽象方法
作用:解决接口升级的问题
接口中默认方法的定义格式
格式:public default 返回值类型 方法名(参数列表){}
范例:public default void show(){}
接口中默认方法的注意事项:
接口中静态方法的定义格式:
接口中静态方法的注意事项:
可以在接口中定义私有方法
格式1:private 返回值类型 方法名(参数列表){}
范例:private void show(){}
格式2:private static 返回值类型 方法名(参数列表){}
范例:private static void show(){}
设计模式是一套反复使用、多数人知晓的、经过分类编目的、代码设计经验的总结。使用设计模式是为了可重用代码、让别人容易理解、保证代码可靠性、程序的重用性。
简单理解:设计模式就是各种套路
适配器设计模式:解决接口与实现类之间的矛盾问题
当一个接口中抽象方法过多,但是我只要使用其中一部分的时候,就可以用适配器的设计模式
书写步骤:
编写中间类xxxAdapter,实现对相应的接口
对接口中的抽象方法进行实现
让真正的实现类继承中间类,并重写需要用的方法
内部类就是在一个类的内部定义一个类,内部类表示的事物是外部类的一部分,内部类单独出现没有任何意义
举例:在A类的内部定义B类,B类就称为内部类
内部类的访问特点:
内部类的分类:成员内部类、静态内部类、局部内部类、匿名内部类
什么是成员内部类
获取内部类的对象
方式一:在外部类中编写方法,对外提供内部类的对象。(一般内部类被private修饰)
public calss Outer{
String name;
private calss Inner{
}
public Inner getInstance(){
return new Inner();
}
}
public class Test{
public class static void main(String[] args){
Outer o = new Outer();
System.out.println(o.getInstance());
}
}
//输出Outer$Inner@4eec777
//输出的意思是某个外部类中的内部类的对象的地址
方式二:直接创建
格式:外部类名.内部类名 对象名 = 外部类对象.内部类对象;
范例:Outer.Inner oi = new Outer().new Inner();
public class Outer{
private int id;
public void out(){
System.out.println("这是外部类的方法");
}
public calss Inner{
public void in(){
System.out.println("这是内部类的方法");
}
public void getId(){//内部类可以访问外部类的私有成员
System.out.println(id);
}
}
}
//在main中创建内部类的对象
Outer outer = new Outer();
Outer.Inner inner = outer.new Inner();
成员内部类如何获取外部类的成员变量
public calss Outer{
private int a = 10;
calss Inner{
private int a = 20;
public void show(){
int a = 30;
System.out.println(Outer.this.a);//10;因为编译器会在内部类的字节码文件中创一个Outer类型的this$0常量,保存的是外部类对象的地址
System.out.println(this.a);//20
System.out.println(a);//30
}
}
}
用static关键字修饰的成员内部类就是静态内部类
静态内部类只能访问外部类中的静态变量和静态方法,如果想要访问非静态方的需要创建对象
外部类名.内部类名 对象名 = new 外部类名.内部类名();
外部类名.内部类名.方法名();
先创建对象,用对象调用
public class Outer{
private int id;
public void out(){
System.out.println("这是外部类的方法");
}
public static calss Inner{//静态内部类
public void in(){
System.out.println("这是内部类的方法");
}
}
}
public class Person{
public void say(){
public class Inner{
}
}
}
匿名内部类:隐藏了名字的内部类,可以写在成员位置,也可以写在局部位置。
匿名内部类的格式:
new 类名或者接口名(){
重写方法;
}
格式的细节
使用场景
public interface UserServices{
void run();
}
//在main方法中
UserServices userservice = new UserServices(){//匿名类
@override
public void run(){
}
};
String name = "123"
//使用String类型的构造方法
//public String() 创建空白字符串不包含任何内容
//public String(String original) 根据传入的字符串,创建字符串对象
//public String(char[] chs) 根据字符数组,创建字符串对象
//public String(byte[] chs) 根据字节数组,创建字符串对象
通过直接赋值的方式创建的字符串是保存在”串池“(StringTable)中的,在jdk7之后,串池保存在堆内存中,在jdk7之前保存在方法区中。串池的特点是不会重复创建相同的字符串,当直接赋值创建的两个字符串的内容相同时,则不会开辟新的空间,而是利用相同的空间,即两个String类型的引用指向相同空间。
通过new关键字创建的字符串,每new一次都会开辟新的空间。
==号比较的是内容,因此当两个基本数据类型的变量比较时,比较的就是这两个变量的内容;当两个引用类型的变量比较时,比较的也是引用类型变量的内容,即地址值。
StringBuilder可以看成是一个容器,创建之后里面的内容是可变的
作用:提高字符串的操作效率
因为StringBuilder是Java改写的类,Java在底层对它做了一些特殊处理,因此打印对象不是地址值而是属性值
public StringJoiner add(添加的内容):添加数据,并返回对象本身
public int length():返回长度(字符出现的个数)
public String toString():返回一个字符串(该字符串就是拼接之后的结果)
字符串拼接的底层原理
等号右边没有变量
public class Test{
public static void main(String[] args){
String s = "a"+"b"+"c";
}
}
拼接时没有变量,都是字符串,触发字符串的优化机制。在编译的时候就已经是最终的结果了
等号右边有变量
JDK7的拼接方式
public class Test{
public static void main(String[] args){
String s1 = "a";
String s2 = s1+"b";
String s3 = s2+"c";
}
}
例如字符串s2 = new StringBuilder().append(s1).append("b").toString;
JDK8的拼接方式
public class Test{
public static void main(String[] args){
String s1 = "a";
String s2 = "b";
String s3 = "c";
String s4 = s1 + s2 + s3;
}
}
拼接时会先预估字符串的长度,这里预估为3,然后创建一个长度为3的数组,数组里面存入"a"、"b"、"c",再把这个整体变为一个字符串
结论:
如果很多字符串变量拼接,不要直接+。在底层会创建多个对象,浪费时间,浪费性能。
StringBuilder源码分析
大小不同
存储类型不同
| 基本数据类型 | 包装类 |
|---|---|
| byte | Byte |
| short | Short |
| char | Character |
| int | Integer |
| long | Long |
| float | Float |
| double | Double |
| boolean | Boolean |
集合中可以存放不同数据类型的数据,但是可以用泛型来限定集合中的元素类型,如:
ArrayList list = new ArrayList();//没有进行限定
ArrayList<String> list = new ArrayList<String>();//JDK7以前的写法,限定数据类型为String
ArrayList<String> list = new ArrayList<>();//JDK7以后的写法,限定数据类型为String
System.out.println(list);
/*
输出:
[]
因为此时创建的对象是ArrayList的对象,而ArrayList是java已经写好的一个类,这个类在底层不是地址值,而是集合中存储的内容,在显示的时候会用[]把所有的数据进行包裹
*/
用来描述一类事物的类。如,Student、Teacher、Dog、Cat
测试类
用来检查其他类是否书写正确,带有main方法的类,是程序的入口
工具类
不是用来描述一类事物的,而是帮我们做一些事情的类,里面的方法大都是静态的,并且构造方法的属性是私有的。
包就是文件夹。用来管理不同功能的Java类,方便后期代码维护
包名的规则:公司域名反写+包的作用,需要全部英文小写,见名知意。
导包的规则(import)
用final修饰:
常量一般作为系统配置信息,方便维护,提高可读性
常量的命名规范:
细节:
final修饰的变量是基本数据类型:那么变量存储的数据值不能发生改变
final修饰的变量是引用类型:那么变量存储的地址值不能发生改变,对象内部的可以改变
分类:
| 修饰符 | 同一个类中 | 同一个包中其他类 | 不同包下的子类 | 不同包下的无关类 |
|---|---|---|---|---|
| private | 可以 | |||
| 空着不写 | 可以 | 可以 | ||
| protected | 可以 | 可以 | 可以 | |
| public | 可以 | 可以 | 可以 | 可以 |
目录前言滤波电路科普主要分类实际情况单位的概念常用评价参数函数型滤波器简单分析滤波电路构成低通滤波器RC低通滤波器RL低通滤波器高通滤波器RC高通滤波器RL高通滤波器部分摘自《LC滤波器设计与制作》,侵权删。前言最近需要学习放大电路和滤波电路,但是由于只在之前做音乐频谱分析仪的时候简单了解过一点点运放,所以也是相当从零开始学习了。滤波电路科普主要分类滤波器:主要是从不同频率的成分中提取出特定频率的信号。有源滤波器:由RC元件与运算放大器组成的滤波器。可滤除某一次或多次谐波,最普通易于采用的无源滤波器结构是将电感与电容串联,可对主要次谐波(3、5、7)构成低阻抗旁路。无源滤波器:无源滤波器,又称
最近在学习CAN,记录一下,也供大家参考交流。推荐几个我觉得很好的CAN学习,本文也是在看了他们的好文之后做的笔记首先是瑞萨的CAN入门,真的通透;秀!靠这篇我竟然2天理解了CAN协议!实战STM32F4CAN!原文链接:https://blog.csdn.net/XiaoXiaoPengBo/article/details/116206252CAN详解(小白教程)原文链接:https://blog.csdn.net/xwwwj/article/details/105372234一篇易懂的CAN通讯协议指南1一篇易懂的CAN通讯协议指南1-知乎(zhihu.com)视频推荐CAN总线个人知识总
深度学习部署:Windows安装pycocotools报错解决方法1.pycocotools库的简介2.pycocotools安装的坑3.解决办法更多Ai资讯:公主号AiCharm本系列是作者在跑一些深度学习实例时,遇到的各种各样的问题及解决办法,希望能够帮助到大家。ERROR:Commanderroredoutwithexitstatus1:'D:\Anaconda3\python.exe'-u-c'importsys,setuptools,tokenize;sys.argv[0]='"'"'C:\\Users\\46653\\AppData\\Local\\Temp\\pip-instal
我完全不是程序员,正在学习使用Ruby和Rails框架进行编程。我目前正在使用Ruby1.8.7和Rails3.0.3,但我想知道我是否应该升级到Ruby1.9,因为我真的没有任何升级的“遗留”成本。缺点是什么?我是否会遇到与普通gem的兼容性问题,或者甚至其他我不太了解甚至无法预料的问题? 最佳答案 你应该升级。不要坚持从1.8.7开始。如果您发现不支持1.9.2的gem,请避免使用它们(因为它们很可能不被维护)。如果您对gem是否兼容1.9.2有任何疑问,您可以在以下位置查看:http://www.railsplugins.or
如何学习ruby的正则表达式?(对于假人) 最佳答案 http://www.rubular.com/在Ruby中使用正则表达式时是一个很棒的工具,因为它可以立即将结果可视化。 关于ruby-我如何学习ruby的正则表达式?,我们在StackOverflow上找到一个类似的问题: https://stackoverflow.com/questions/1881231/
深度学习12.CNN经典网络VGG16一、简介1.VGG来源2.VGG分类3.不同模型的参数数量4.3x3卷积核的好处5.关于学习率调度6.批归一化二、VGG16层分析1.层划分2.参数展开过程图解3.参数传递示例4.VGG16各层参数数量三、代码分析1.VGG16模型定义2.训练3.测试一、简介1.VGG来源VGG(VisualGeometryGroup)是一个视觉几何组在2014年提出的深度卷积神经网络架构。VGG在2014年ImageNet图像分类竞赛亚军,定位竞赛冠军;VGG网络采用连续的小卷积核(3x3)和池化层构建深度神经网络,网络深度可以达到16层或19层,其中VGG16和VGG
文章目录1、自相关函数ACF2、偏自相关函数PACF3、ARIMA(p,d,q)的阶数判断4、代码实现1、引入所需依赖2、数据读取与处理3、一阶差分与绘图4、ACF5、PACF1、自相关函数ACF自相关函数反映了同一序列在不同时序的取值之间的相关性。公式:ACF(k)=ρk=Cov(yt,yt−k)Var(yt)ACF(k)=\rho_{k}=\frac{Cov(y_{t},y_{t-k})}{Var(y_{t})}ACF(k)=ρk=Var(yt)Cov(yt,yt−k)其中分子用于求协方差矩阵,分母用于计算样本方差。求出的ACF值为[-1,1]。但对于一个平稳的AR模型,求出其滞
写在之前Shader变体、Shader属性定义技巧、自定义材质面板,这三个知识点任何一个单拿出来都是一套知识体系,不能一概而论,本文章目的在于将学习和实际工作中遇见的问题进行总结,类似于网络笔记之用,方便后续回顾查看,如有以偏概全、不祥不尽之处,还望海涵。1、Shader变体先看一段代码......Properties{ [KeywordEnum(on,off)]USL_USE_COL("IsUseColorMixTex?",int)=0 [Toggle(IS_RED_ON)]_IsRed("IsRed?",int)=0}......//中间省略,后续会有完整代码 #pragmamulti_c
按照目前的情况,这个问题不适合我们的问答形式。我们希望答案得到事实、引用或专业知识的支持,但这个问题可能会引发辩论、争论、投票或扩展讨论。如果您觉得这个问题可以改进并可能重新打开,visitthehelpcenter指导。关闭9年前。我来自C、php和bash背景,很容易学习,因为它们都有相同的C结构,我可以将其与我已经知道的联系起来。然后2年前我学了Python并且学得很好,Python对我来说比Ruby更容易学。然后从去年开始,我一直在尝试学习Ruby,然后是Rails,我承认,直到现在我还是学不会,讽刺的是那些打着简单易学的烙印,但是对于我这样一个老练的程序员来说,我只是无法将它
按照目前的情况,这个问题不适合我们的问答形式。我们希望答案得到事实、引用或专业知识的支持,但这个问题可能会引发辩论、争论、投票或扩展讨论。如果您觉得这个问题可以改进并可能重新打开,visitthehelpcenter指导。关闭10年前。有没有学习Ajax(jQuery)和Rails3的好资源?