1.方法注意事项
(1)一个方法最多有一个返回值,返回多个值可以设置成返回数组
public class A{
public static void main(String[] args){
AA aa=new AA();
int res[]=a.getSum(5,2);
}
}
class B{
public int[] getSum(int m,int n){
int arr[]=new int[];
arr[1]=m+n;
arr[2]=m-n;
return arr[];
}
}
(2)返回类型可以是任何类型,包括基本和引用(数组,对象)
(3)如果方法要求有返回值,则最后一行执行语句应为return ,且类型应一致
(4)如果方法为void,可以没有return或者只写return
(5)参数类型可以为任意类型,包括基本和引用
(6)形参实参类型个数顺序必须相同
(7)方法体中不能再定义方法,方法不能嵌套定义
2.方法调用
(1)同一个类中的方法可以直接调用
(2)跨类调用:先创建对象再调用
PS:a.m1()在void main(String[] args)被调用时,先输出“m1()被调用”,再执行并输出hi(),再返回void m1()
Eg:判断奇偶
Eg:打印m行n列随意字符
public class Hello{
public static void main(String[] args){
AA a=new AA();
a.pChar(2,5,'#');
}
}
class AA{
public void pChar(int row,int col,char c){
for(int n=1;n<=row;n++){
for(int m=1;m<=col;m++){
System.out.print(c);
}
System.out.println();
}
}
}
3.方法传参
(1)基本数据类型的传参
基本数据类型传参时,调用不同的栈中的变量,变量值只与本栈有关
(2)引用数据类型传参
栈:主栈(main):B b=new B();指向堆里一个对象 1
int[] arr= ;指向堆里一个地址[0X1100] 2
b.test100(arr);调用方法,产生一个新的栈 3
遍历输出 7
栈test100(被调用而产生) arr= ;指向堆里的[0X1100] 4
arr[0]=100; [0X1100]的第一个数值变为100 5
遍历输出 6
堆: B对象 [0X1100]
(方法区:)
4.p:引用数据类型
main{
B b=new B();
Person p=
p.name=
p,age=10;
b.teat200(p);
System(p.age);//10000
}
class Person{
String name;
int age;
}
class B{
public void test200(Person p){
p.age=10000;
}
}
p置空:不指向堆,等于10
Eg:new person 再new person(???????)
main栈 p.age=10,指向堆的一个person对象 b.test200(p)开新栈
test200栈(原本Person p指向main的p.age所在的对象) new一个person,指向堆一个新的person对象,与main里p.age所在对象的联系断开 p.age=99
main栈 输出main栈的p.age,=10
5.克隆对象
public{
main{
Person p=new Person();
p.age=100;
MyTools tools=new MyTools();
Person p2=tools.copyPerson();
}
}
class Person{
int age;
}
class MyTools{
public Person copyPerson(Person p){
Person p2=new Person();
p2.age=p.age;
return p2;
}
}
6.方法递归调用举例
7.阶乘 递归
main调用:int res=t1.factorial(5); System.out.println(res);
main栈: f(5),返回f(4)*5,调用f();新开栈f(4)*5,调用f();新开栈f(3)*4,调用f();新开栈f(2)*3,新开栈f(1)*2;调用f();n=1,return1到f(1);return f(1)*2=2到f(2);..........
18注意事项
(1)调用方法就会开新栈
(2)方法的局部变量互相独立
(3)引用数据类型的数据同步(传的是地址)
(4)递归必须向退出递归的条件逼近,不然会出现无限递归StackOverflowError
(5)方法执行完或有return,遵循谁调用返回谁原则
9.方法重载(OverLoad):允许同一个类中多个方法同名,但要求形参列表不一致
重载减轻了起名、记名的麻烦
10.重载注意事项
(1)方法名必须相同
(2)形参列表必须不同(形参类型、个数或顺序至少有一样不同,参数名无要求)
(3)返回类型无要求
11.可变参数:JAVA允许同一个类中多个同名同功能但参数个数不同的方法封装成一个方法
举例:
PS.(1)可变参数可以和普通类型参数同时出现,但可变必须在最后
(2)一个形参列表中只能有一个可变参数
12.作用域
变量:属性(成员变量),局部变量(成员方法中定义的变量)
作用域:全局变量(属性,作用域为整个类体),局部变量(除了属性之外的其他变量,作用域为定义它的代码块)
PS.全局变量(属性,默认值同数组)可以不赋值直接用,因为有默认值;局部变量要先赋值才能使用,没有默认值
class Cat{
int age=10;
//全局变量:属性,作用域为整个类体
//可以不赋值直接使用
double weight;//默认值为0.0
public void cry(){
int n=10;
String name="yaemiko";
//n,name是局部变量,作用域在cry()中,必须先赋值
}
}
13.作用域原则
(1)属性和局部变量可以重名,访问时遵循就近原则
输出king
(2)同一个作用域中,两个局部变量不能重名
(3)属性生命周期较长,伴随对象的创建而创建,伴随对象的死亡而死亡;
局部变量生命周期较短,伴随定义它的代码块的创建而创建,伴随代码块死亡而死亡,即一次方法调用过程
(4)作用域范围不同
全局变量:可以被本类使用,也可以被其他类通过对象调用使用后
局部变量:只能在本类对应方法中使用
(5)修饰符不同
全局变量(属性)可以加修饰符,局部变量不可以加修饰符
14.构造器/构造方法:[修饰符] 方法名(形参列表){ 方法体 }
PS.(1)构造器的修饰符可以默认
(2)没有返回值
(3)方法名和类名保持一致
(4)参数列表和成员方法类似
(5)构造器调用由系统完成。在调用对象时,系统会自动调用该类的构造器完成对对象的初始化
//创建Person
对象时,直接指定对象的年龄和姓名
class Person{
String name;
int age;
//构造器没有返回值,也不能写void
//构造器名称和类名一样,即Person
public Person(String pName,int pAge){//形参列表规则类似成员方法的形参列表
name=pName;
age=pAge;
}
}//构造器被调用时,完成对象的属性初始化
15.构造器细节
(1)一个类可以定义多个构造器,即构造器重载
cclass {
String name;
int age;
public Person(String name,int age){
.....
}
//第一个构造器
public Person(String name){
....
}
//第二个构造器
}
(2)构造器名和类名相同且没有返回值
(3)构造器是完成对象初始化,不是创建对象
(4)创建对象时,系统会自动调用本类的构造方法
(5)如果没有定义构造方法,系统会自动生成一个该类的默认无参构造方法
(6)一旦定义了自己的构造器,默认的构造器会被覆盖且不能再使用,除非显式定义
16.对象创建的流程分析
class Person{ //(1)方法区加载Perdon类
int age=10; //(3)初始化[0X0011]:age=0,name=null;(4)age=10
String name;
Person(String n,int a){
name=n;
age=a;
}
}
Person p=new Perrson("小明",20); //(2)堆里开空间[0X0011]
//(5)调用构造器,方法区常量池开空间[0X0022],指向堆的name,即name空间地址变为[0X0022]
//(6)20赋给堆里的age
17.this
public{
static main{
Dog d1;
d1.info();
}
}
class Dog{
String name;
int age;
public info(String name,int age){
name=name;
age=age;//构造器就近,两个都是形参
}
}
//this.name=name;this.age=age;
//this:谁调用就是谁(d1)
//d1.name;d1.age
18.this 的内存理解
19.hashCode()方法:返回对象的hash码值,一般是把对象的内部地址转换成一个整数
20.this关键字注意事项