/*
? 以下程序不使用方法,分析程序存在哪些缺点?
??? *以下的代码都是完成两个int类型数据的和,相同的代码写了三遍(只不过每一次参与求和的数据不同)
??? 代码没有得到重复使用。
??? *应该在java语言当中有这样的一种机制:
??????? -某个代码只需写一遍
??????? -要使用这个功能,只需要给这个功能传递具体的数据
??????? -这个功能完成之后返回一个最终的结果
?????? 这样代码就可以重复利用了,提高代码复用性。【这就是“方法”】
???? 使用这个方法我们称为“调用/invoke"
*/
? public class Method1{
??? public static void main (String [] args){
?????? //需求1:请编写程序计算10和20的和,并将结果输出【功能:计算两个int类型数据的和】
?????? int a = 10;
?????? int b = 20;
?????? System.out.println(a+"+"+b+"="+c);
????? //需求2:请编写程序计算666和888的和,并将结果输出【功能:计算两个int类型数据的和】
?????? int x = 666;
?????? int y = 888;
?????? System.out.println(x+"+"+y+"="+z);
?????? //需求3:请编写程序计算111和222的和,并将结果输出【功能:计算两个int类型数据的和】
?????? int m= 111;
?????? int n = 222;
?????? System.out.println(m+"+"+n+"="+e);
???? }
?}
??? //以上的三个需求其实是一个需求,这个需求是:计算两个int类型数据的和,功能相同。
?????? 只不过每一次参与计算的具体数据不同。
/*以下程序直接使用方法,分析程序的优点?
?? *代码得到了重复利用
?方法的本质是什么?
?? *方法就是一段代码片段,并且这段代码片段可以完成某个特定的功能,并且可以被重复使用。
?方法对应的英语单词是:Method
?方法在C语言中叫做函数/Function
?
? 方法定义在类体当中,在一个类当中可以定义多个方法,方法编写的位置没有先后顺序,可以随意。
? 方法体当中不能再定义方法!
? 方法体由java语句构成,方法体当中的代码遵守自上而下的顺序依次执行
*/
?public class Method2{
?? public static void main(String[] args){
??? //计算两个int类型数据的和
??? Method2.sumInt(10,20);
??? Method2.sumInt(666,888);
??? Method2.sumInt(111,222);
?? }
?? //单独定义一个方法,该方法完成计算两个int类型数据的和,并将结果输出
?? public static void sumInt(int a,int b){
???? int c = a+b;
???? System.out.println(a+"+"+b+"="+c);
?? }
}
??
?关于java语言当中的方法:
? 1.方法怎么定义,语法结构:
???? 【修饰符列表】 返回值类型 方法名(形式参数列表){
???????? 方法体;
????? }
?2.对以上的语法结构进行解释说明:
?? 2.1 关于修饰符列表
???????? *可选项,不是必须的
???????? *目前统一写成:public static
???????? *方法的修饰符列表当中有"static"关键字的话,怎么调用这个方法?
???????????? —类体.方法名(实际参数列表);? //”.“可以理解为中文的”的“字
?? 2.2返回值类型
?????? *什么是返回值?
????????? 一个方法是可以完成某个特定功能的,这个功能结束之后大部分都是需要返回
????????? 最终执行的结果,执行结果可能是一个具体存在的数据,而这个具体存在的数
????????? 据就是返回值。
?????? *返回值类型?
???????? 返回值是一个具体存在的数据,数据都是有类型的。此处需要指定的是返回值
???????? 的具体类型。
?????? *返回值类型都可以指定哪些类型呢?
????????? java任意一种类型都可以,包括基本数据类型和所有的引用数据类型
?????? *也可能在这个方法执行结束之后不返回任何数据,,java中规定,但一个方法
??????? 执行结束之后不返回任何数据的话,返回值类型位置必须编写:void关键字。
?????? *返回值类型可以是:
????????? byte,short,int,long,float,double,boolean,char,String,void ……
?????? *返回值类型若不是void,表示这个方法执行结束之后必须返回一个具体的数值。
???????? 当方法执行结束的时候没有返回任何数据的话编译器会报错
?????????? 怎么返回值呢 代码怎么编写?
????????????? ”return 值;“ 并且要求”值“的数据类型必须和”方法的返回值类型一致,
???????? 不然编译器报错。
?????? *返回值类型是void的时候,在方法体当中不能编写“return 值;"这样的语句。
???????? 但是可以编写“return;"这样的语句。
?????? *只要带有return关键字的语句执行,return语句所在的方法结束【不是JVM结束,
???????? 是return所在的方法结束】
? 2.3方法名
?????? *方法名最好是动词
?????? *方法名首字母要求小写,后面每个单词首字母大写
?2.4形式参数列表,简称形参
????? *形参是局部变量:int a; double b;float c;String s; ……
????? *形参的个数可以是:0-N个
????? *多个形参之间用”逗号“隔开
????? *形参中起决定作用的是形参的数据类型,形参的名字就是局部变量的名字
????? *方法在调用的时候,实际给这个方法传递的真实数据被称为:实际参数,简称实参
????? *实参列表和形参列表必须满足:
??????????? 数量相同,类型对应相同
? 2.5方法体必须由大括号括起来,方法体当中的代码有顺序,遵循自上而下的顺序依次执行。
????? 并且方法体由java语句构成,每一个java语句以”;“结尾
3.方法怎么调用?
?? 方法只定义不去调用时不会执行,只有在调用的时候才会执行。
?? 语法规则:《方法的修饰符列表当中有static》
????? 类名.方法名(实参列表);<这是一条java语句,表示调用某个类的某个方法,传递这样的实参。>
public表示公开
static表示静态
void表示方法执行结束之后不会返回任何数据
main是方法名:主方法
(String[] args):形式参数列表,其中String[]是一种引用数据类型,args是一个局部变量的变量名,所以只有args这个局部变量的变量名是随意的
主方法就需要这样固定编写,这就是程序的入口。【SUN规定的,必须这样写】
主方法的程序是JVM负责调用的,是一个入口位置,这里的程序是一定会执行的,从这里作为起点开始执行操作
自定义方法不是程序的入口
一个方法可以被重复使用,重复调用
方法体当中的代码是有顺序的,遵循自上而下的顺序依次执行,上一行程序执行不结束,无法执行下一行程序
方法调用的时候实参和形参要求个数对应相同,数据类型对应相同。
类型不同的时候要求能够进行相应的自动类型转换
方法调用:
?1.方法的修饰符列表当中有static关键字时,完整的调用方法是:类名.方法名(实参列表);
?2.但是,有的时候”类名.“可以省略,什么情况下可以省略呢?
????? m1( ){
???????????? m2( )
????? }
? m1方法和m2方法在同一个类体当中的时候,”类名.“可以省略不写
3.建议在java源程序当中只定义一个类,比较清晰
方法的返回值类型不是void的时候。
? 1.返回值类型不是void的时候:
????? 要求方法必须保证百分百的执行"retuen 值;"这样的语句来完成值的返回。
????? 没有这个语句编译器会报错。
? 2.一个方法有返回值的时候,当我们调用这个方法时,方法返回一个值,对于调用者来说,这个返回值可以选择接收,也可以选择不接收。
? 但大部分情况下会接收
??? 采用变量接收,变量的数据类型需要和返回值的数据类型相同,或者可以自动类型转换
?????? 例: int i=divide(10,3);
????????????? System.out.println(i);
深入return语句
? *带有return关键字的java语句只要执行,所在的方法执行结束
? *在“同一个作用域”当中,return语句下面不能编写任何代码,因为这些代码永远都执行不到,编译器会报错。
? *在返回值类型时void方法当中使用“return;"语句,”return;"语句出现在返回值为void的方法中主要是为了用来结束当前方法。
方法在执行过程中,在JVM中的内存是如何分配的,内存是如何变化的?
?? 1.方法只定义,不调用,是不会执行的,并且在JVM中也不会给该方法分配“运行所属”的内存空间。只有在调用这个方法的时候,才会动态的给这个方法分配所属的内存空间。
?? 2.在JVM内存划分上有这样三块主要的内存空间(当然除了这三块之外还有其他的内存空间):方法区内存?? 堆内存?? 栈内存
?? 3.关于“栈”数据结构:
????????? *栈:stack,是一种数据结构,数据结构反应的是数据的存储形态,数据结构是独立的学科,不属于任何编程语言的范畴,只不过在大多数编程语言当中要使用数据结构。
????????? *作为程序员需要提前精通:数据结构+算法【计算机专业必修一门课程】
????????? *常见的数据结构:数组? 队列? 栈? 链表? 二叉树? 哈希表/散列表
?? 4.方法代码片段存在哪里?方法执行的时候执行过程的内存在哪里分配?
?????? *方法代码片段属于.class字节码文件的一部分,字节码文件在类加载器的时候,将其放到了方法区当中。所以JVM中的三块主要的内存空间中方法区内存最先有数据,存放了代码片段
?????? *代码片段虽然在方法区内存当中只有一份,但是可以被重复调用。每一次调用这个方法的时候,需要给该方法分配独立的活动场所,在栈内存中分配。【栈内存中分配方法运行的所属内存空间】
? 5.方法在调用的瞬间,会给该方法分配内存空间,会在栈中发生压栈动作,方法执行结束之后,给该方法分配的内存空间全部释放,此时发生弹栈动作。
?????? *压栈:给方法分配内存
?????? *弹栈:释放该方法的内存空间
? 6.局部变量在“方法体”中声明。局部变量运行阶段内存在栈中分配
?public class MethodTest01{
??? public static void main(String[] args){
??????? int a = 10;
??????? int b = 20;
??????? int retValue = sumInt(a,b);
??????? System.out.println("retValue ="+retValue);
??? }
??? public static int sumInt(int i,int j){
??????? int result = i+j;
??????? int num = 3;
??????? int retValue = divide(result,num);
??????? return retValue;
?? }
?? public static int divide(int x,int y){
????? int z = x/y;
????? return z;
? }
}
以下代码不使用“方法重载机制”,分析程序存在的缺点?
??? 1.sumInt sumDouble sumLong方法虽然功能不同,但是功能是相似的。都是求和。
?? 在以下程序当中功能相似的方法,分别起了三个不同的名字,这对于程序员来说,调
?? 用方法的时候不方便,程序员需要记忆更多的方法,才能完成调用。【不方便】
??? 2.代码不美观
?有没有这样一种机制:
???? 功能虽然不同,但是“功能相似”的时候,可以让程序员使用这些方法的时候就像在使
用同一个方法一样,这样程序员以后编写代码比较方便,也不需要记忆更多的方法名。代码
美观。
? 有这种机制:方法重载机制/Overload
? java支持这种机制【有些语言不支持,例如:javaScript】
? public class OverloadTest1{
????? public static void mian(String[] args){
????????? //调用方法
????????? int result1 = sumInt(1,2);
????????? System.out.println(result1);
????????? double result2 = sumDouble(1.0,2.0);
????????? System.out.println(result2);
????????? long result3 = sumLong(1L,2L);
????????? System.out.println(result3);
????? }
????? //定义一个方法,可以计算两个int类型数据的和
????? public static int sumInt(int a,int b){
?????????? return a+b;
????? }
????? //定义一个方法,可以计算两个double类型数据的和
????? public static double sumDouble(double a,double b){
????????? return a+b;
????? }
????? //定义一个方法,可以计算两个long类型数据的和
????? public static void sumLong(long a,long b){
????????? return a+b;
????? }
}
体验“方法重载机制”,分析方法重载的优点?
??? *程序员调用方法的时候比较方便,不需要记忆更多的方法名,代码美观
??? *参数的类型不同,对应调用的方法不同,此时区分方法不再依靠方法名了,依靠的是参数的数据类型
??? *前提:功能相似的时候,方法名可以相同
??????????????? 但是,功能不同的时候,尽可能让这两个方法的名字不同
???? public class OverloadTest2{
????????? public static void main(Sting[] args){
??????????? System.out.println(sum(1,2));
??????????? System.out.println(sum(1.0,2.0));
??????????? System.out.println(sum(1L,2L));
????????? }
????????? public static int sum(int a,int b){
?????????????? return a+b;
?????????? }
?????????? public static double sum(double a,double b){
?????????????? return a+b;
?????????? }
?????????? public static long sum(long a,long b){
?????????????? return a+b;
?????????? }
}
方法重载:
??? 1.方法重载又被称为:overload
??? 2.什么时候考虑使用方法重载?
????????? 功能相似的时候,尽可能让方法名相同
??? 3.什么条件满足之后构成了方法重载?
???????? *在同一个类当中
???????? *方法名相同
???????? *参数列表不同
???????????? 数量不同 顺序不同 类型不同
??? 4.方法重载和什么有关系,和什么没关系?
??????? *方法重载和方法名+参数列表有关系
??????? *方法重载和返回值类型无关
??????? *方法重载和修饰符列表无关
六、方法递归
关于方法的递归调用
???? 1.什么是递归?
?????????? 方法自身调用自身
??????????????? a( ){
??????????????????? a( );
?????????????? }
???? 2.递归是很耗费栈内存的,递归算法可以不用的时候尽量不用
???? 3.出现? java.lang.StackOverflowError
??????? 说明栈内存溢出错误,错误发生无法挽回,只有一个结果,就是JVM停止工作
???? 4.递归必须有结束条件,没有结束条件一定会发生栈内存溢出错误。
???? 5.递归即使有了结束条件,即使结束条件是正确的,也可能会发生栈内存溢出错误,因为递归的太深了
? public static int faction(int n){
?? if(n==0)
????? return 1;
?? else
????? return n*faction(n-1);
?? }