Java笔记整理 —— 方法调用机制与递归调用机制

方法调用机制

Person p1 = new Person();
int res = p1.getSum(10,20);
System.out.println("值="+res);

public int getSum(int num1,int num2){
    int res = num1 + num2;
    return res;
}

1. 当程序执行到方法时,会在栈里单独开辟一个空间(这也是为什么swap无法使用的原因)。

2. 当方法执行完毕,或者执行到return语句时,就会返回。

3. 返回到调用方法的地方。

4. 返回后继续执行方法后面的代码。

5. 当main方法执行完毕,整个程序退出。

方法调用细节

 1. 同一个类中的方法调用

直接调用即可。

 2. 跨类中 A类调用B类的方法

      需要通过新建对象,用 对象名.方法名(参数) 进行调用。(注意这种跨类调用要符合访问修饰符的限制)

class first {
	public void Hi() {
		System.out.print("Hi!");
	}
}

class second {
	public void useA()
	{
		first a = new first(); //构建一个对象
		a.Hi(); //调用跨类的方法
	}
}

 3. 传递的参数为引用类型详解

public class Practice {
	public static void main(String[] args) {
         Person a = new Person();
         a.age = 20;  //初始化的属性值
         Test p = new Test();
			p.test01(a);
         System.out.print(a.age);
	}
}

class Person {
	int age;
	String name;
}

 对象的属性修改为另一个值:

class Test {
	public void test01(Person b) {  //传递一个对象(引用传递)
		b.age = 100000;  //修改对象的属性
	}
}

让对象指向null:

class Test {
	public void test01(Person b) {
		b = null;  //对象指向null
	}
}

初始化对象:

class Test {
	public void test01(Person b) {
		b = new Person();
	}
}

    可以发现,当传入一个对象时,只有修改对象属性值才会生效,如果把对象指向null,或者让对象指向一个刚new的新对象,对原来的对象并没有什么影响。这是为什么呢?这里就需要考虑到方法调用机制了。

    当调用test方法,传入一个对象时,实际上在栈里新开辟了一个空间,在这个空间里创建了一个Person对象 b(参考调用机制),接收传入对象的地址实际上传入的是地址,注意与C++的引用不同,可以说类似于指针)。

      然后 b 就指向堆区域的实际对象了,对 b 的属性进行修改,其实就是对实际对象进行修改。但是,如果把null赋给b,实际上只是 b 指向了null,对主函数声明的 a 没有任何影响,new也是同理,只有 b 指向了一个新的对象,而主函数声明的 a 仍然指向原来的对象。因此,最后输出的都是20。

4. 修改String属性的理解

public static void main(String[] args) {
		Person a = new Person();
		Person b = new Person();
		a.name = "milan";
		b.name = "milan";
		System.out.println(a.name);
		System.out.println(b.name);
		b.name = "shang";
		System.out.println("==========");
		System.out.println(a.name);
		System.out.println(b.name);
	}

  已知String是一个类,因此Person的name属性也是存放的地址。根据上面的代码,a和b的名字相同,name都指向"milan"。这时候修改b的name为"shang",那么a的name属性会不会发生变化?

  是不会的。修改b的name的实质,并不是修改对应地址的内容,而是重新开辟了一块区域,里面的内容是"shang",然后把这个地址赋给b.name,对原先"milan"所在区域没有任何影响

递归调用机制

  1. 输出递归

class Person {
	public void test(int n) {
		if(n>2)
			test(n-1);  //递归调用
		System.out.println("n的值为: " + n);
	}
}
//主函数
Person a = new Person();
a.test(4);

由于只是值传递,因此每一层中n的值并不会被下一层改变,最终结果为:

 2. 阶乘

public int factorial(int n) {  //假设n为5
		if (n == 1) {
			return 1;
		} else {
			return factorial(n - 1) * n;
		}
	}

 递归调用示意图如下: 

 

 3. 递归重要规则

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值