为什么需要方法?方法是怎么来的?
-
因为我们写代码的过程中往往会遇到一些重复性且功能相同的语句,我们可以将这些重复的语句抽取出来,组成一个可以重复使用的代码块。这种代码块就叫做方法
-
概念:完成特定的一个功能的一个代码块
-
可以完成特定的一个功能且可以重复调用的一个代码块
-
定义一个方法的语法
public static void method(){ System.out.println("这是第一个方法"); } // 修饰符 返回值类型 方法名(参数列表){ // 方法体; //}
修饰符
- public static 目前就记住这一个,等以后学到更多再回来补充
返回值类型
- 整数类型
- byte、short、int、long
- float、double
- char
- boolean
- 引用类型
- String、数组、接口?接口需要另外创建一个实现类,来重写接口中的抽象方法
方法名遵循什么规范和规则
- 规范
- 小驼峰命名法
- 首字母小写 (类名是首字母大写的驼峰命名法)
- 规则
-
- 可以使用数字、字母、_ 、$进行命名
- 方法名开头不能时候数字
- 方法名不能使用关键字和标识符
-
- 参数列表中可以填什么类型的参数
- 与返回值类型一致
定义一个方法有多少中形式?
-
无参数,无返回值
public static void method(){ System.out.println("无参数,无返回值!!"); }
-
无参数,有返回值
public static int method2(){ int a = 10; return a; }
-
有参数,无返回值
public static void method3(int a){ System.out.println("你输入的值是" + a); }
-
有参数,有返回值
public static int method(int a,int b){ return a + b; }
注意事项:
- 方法必须定义在类中,在Java中最小的程序单元是类,必须先有类
- 一个类中可以定义多个方法
- 方法和方法是平行的,不能在方法中定义另外一个方法
- 方法的定义没有先后顺序
调用
调用的语法
-
在本类中调用
-
有返回值:需要使用一个变量接收返回值
-
调用语法
返回值类型 变量 = 方法所在的类名.方法名(实际参数);
-
如果方法使用了static进行修饰,可以将方法所在的类名进行省略
-
-
-
调用的时候,传递的参数就是实际参数,简称实参,和顺序、类型有关
方法的一些练习
- 需求1:定义一个方法,打印指定行数的指定字符串
public class Demo02Method {
public static void main(String[] args) {
// 定义一个方法,打印指定行数的字符串
printStr(3, "XXX");
// 定义一个方法,传入一个int类型 按照指定格式(格式:[X,X])打印int类型数组
// 创建一个数组
int[] a = {1, 2, 3, 4};
System.out.println(printArray(a));
}
/**
* 需求1
*/
public static void printStr(int num, String str) {
for (int i = 1; i <= num; i++) {
System.out.println(str);
}
}
}
- 需求2:定义一个方法,传入一个int数组,按照指定格式(格式[XXX])打印int类型数组
public class Demo02Method {
public static void main(String[] args) {
// 定义一个方法,打印指定行数的字符串
printStr(3, "XXX");
// 定义一个方法,传入一个int类型 按照指定格式(格式:[X,X])打印int类型数组
// 创建一个数组
int[] a = {1, 2, 3, 4};
System.out.println(printArray(a));
// 定义一个方法,输出给定行的乘法表
/*
1. 给定行 === 接收一个int参数
2. 输出乘法表 直接输出 void 没有返回值
*/
printMultiTable(5);
}
/**
* 需求2
*/
public static String printArray(int[] arr) {
String str = "[";
for (int i = 0; i < arr.length; i++) {
str += arr[i];
if (i == arr.length - 1) {
str += "]";
} else {
str += ",";
}
}
return str;
}
}
- 需求3:定义一个方法,传入一个int数组,返回指定元素在数组中第一次出现的索引
public class Demo03Method {
public static void main(String[] args) {
// 创建一个数组
int[] array = {1,2,3,4222,444,123123,333,666};
// 使用第一个方法
System.out.println(indexOf(array,666));
}
public static int indexOf(int[] arr, int a) {
for (int i = 0; i < arr.length; i++) {
if (a == arr[i]) {
return i;
}
}
// 如果没有找到 就返回-1
return -1;
}
public static int indexOf2(int[] arr, int a) {
int index = -1;
for (int i = 0; i < arr.length; i++) {
if (a == arr[i]) {
index = i;
break;
}
}
return index;
}
}
方法的可变参数
格式
[修饰符] 返回值类型 方法名称(参数类型 参数1,,,参数类型...参数名)
{
方法体;
[return 返回值;]
}
-
方法的可变参数可以看成是一个一维数组
-
可变参数必须作为方法中参数列表的最后一个参数,避免多个参数的歧义性。
-
推论:方法最多就只有一个可变参数。
-
需求5:定义一个方法,传入两个参数,一个double数组表示多个货品的价格,一个double类型的折扣,返回货品总价格
/**
* @program: wolfcode
* @author: Mr.Gao
* @Date: 2021/01/13 14:46
* <p>
* 方法的可变参数
* 方法的可变参数在传入方法时,作为一个数组对待,在方法内作为一个数组使用
* 可变参数一定要作为方法中的最后一个参数
*/
public class Demo04Method {
public static void main(String[] args) {
// 创建一个数组
double[] price = {1.0,2.5,4.4};
// 这种方法
System.out.println(getTotalPrice(0.8, price));
}
/**
* 定义一个方法,传入两个参数,一个double数组类型表示
* 创建一个方法 ,将数组输入 将折扣输入 求出打折之后的总价
*/
public static double getTotalPrice(double discount, double... price) {
// 创建一个参数用于存储数组的总价
double total = 0.0;
for (double item : price) {
total += item;
}
return total * discount;
}
}
方法的重载
方法重载的判断依据
- 普通判断:在同一个类中,有相同的方法名但是不同参数列表的多个方法称为重载。
- 同一个类中
- 方法名相同
- 参数列表不同(参数的顺序、参数的类型、参数的个数)
- 方法签名判断:在同一个类中,可以存在名称相同但是方法签名不同的多个方法称为重载。
方法重载的作用
- 屏蔽了同一功能的方法由于参数不同所造成的方法名称不同。
方法参数的值传递机制
值传递
- 方法在调用过程中,把实参的值复制一份给形参的过程称为值传递。java方法调用时的值传递过程就采用值传递。
基本类型参数
public class Demo07Method {
public static void main(String[] args) {
int m = 10;
change(m);
System.out.println("m = " + m);
}
/**
* 值传递,传递的是m中实实在在的值给a
*/
public static void change(int a){
a = 100;
}
}
- 输出结果
m = 10
引用类型参数
public class Demo07Method {
public static void main(String[] args) {
int[] arr = {1,2,3};
change(arr);
System.out.println(arr[0]);
}
/**
* 值传递:复制传递的是arr中的地址值给array
*/
public static void change(int[] array){
array[0] = 100;
}
}
输出结果
100
递归
-
方法调用自身的现象称之为递归
-
递归的两个要素
- 递归的停止条件
- 递归体
-
递归的使用场景和问题特征:
- 当解决一个问题时,可以分为多层步骤
- 外层解决问题的步骤和内层解决问题的步骤一样
- 外层问题依赖内层问题的解决
- 内层问题解决了,外层问题自然解决
-
需求1:求n的阶乘
public class Demo08Method {
public static void main(String[] args) {
long r = fact(5);
System.out.println("5的阶乘是:\t" + r);
}
/**
* 求n的阶乘
*/
public static long fact(int n) {
// 首先要有判断结束的语句
if (n == 1) {
return 1;
}
return n * fact(n - 1);
}
}
- 需求2:斐波那契数列
public class Demo09Method {
public static void main(String[] args) {
for (int i = 1; i <= 2; i++) {
System.out.print(feibo(i) + "\t");
}
}
public static int feibo(int n) {
if (n <= 2) {
return 1;
}
return feibo(n - 1) + feibo(n - 2);
}
}
eturn n * fact(n - 1);
}
}
+ 需求2:斐波那契数列
~~~java
public class Demo09Method {
public static void main(String[] args) {
for (int i = 1; i <= 2; i++) {
System.out.print(feibo(i) + "\t");
}
}
public static int feibo(int n) {
if (n <= 2) {
return 1;
}
return feibo(n - 1) + feibo(n - 2);
}
}