【Java】方法的使用

简介: 【Java】方法的使用

1.方法的概念和使用

1.1 为什么需要方法

假设你是班长,学生需要到学校的某个地方领书。但是学生都不知道领书地在哪里,于是学生都纷纷在QQ私聊上来问你,一会儿来一个 一会儿又来一个,每一个学生都是来问领书地的,然后你的回答都是教学楼门口领书。每一次都是一样的回答,但是又要一直这样回复,这样就显得很麻烦。


那有什么方法可以解决这个重复又麻烦的问题了?


答:可以直接在QQ班级群发在 教学楼门口 领书,这样班级里的同学都可以看到了。要是还有人问你,你就可以让他去看QQ群,这样就可以解决这个问题了


上述的问题例子就充分了解为什么需要方法了


因此,在编程中,我们也可以将频繁使用的代码封装成方法,需要时直接拿来方法名使用即可,避免了一遍一遍的重复,这样不仅能让代码不冗余,还能提高代码的可读性


1.2 方法的概念

方法就相当于C语言中的函数,具有独立性,可以独立完成某个功能,只要调用这个方法就可以完成这个功能


是能够模块化的组织代码(当代码规模比较复杂的时候).

做到代码被重复使用, 一份代码可以在多个位置使用.

让代码更好理解更简单.

比如:输入一个年份,判断是否为闰年?


import java.util.Scanner;

public class Test {
    public static void main(String[] args) {
        Scanner scanner = new Scanner(System.in);
        int year = scanner.nextInt();
        if (year % 4 == 0 && year % 100 != 0 || year % 400 == 0) {
            System.out.println("yes");
        } else {
            System.out.println("no");
        }
    }
}

上述代码 if  else 就是判断是否为闰年的,那接下来我们就将判断闰年的代码封装成方法


import java.util.Scanner;
public class Test {
    public static void isLeapYear(int year) {
        if (year % 4 == 0 && year % 100 != 0 || year % 400 == 0) {
            System.out.println("yes");
        } else {
            System.out.println("no");
        }
    }
    public static void main(String[] args) {
        Scanner scanner = new Scanner(System.in);
        int year = scanner.nextInt();
        isLeapYear(year);
    }
}

这样就将判断闰年的代码封装成方法了,这样主函数看起了就比较简洁了。当我们在主函数中看到了  isLeapYear(year) 我们就知道了需要调用 isLeapYear 这个方法了。


方法语法格式:


前.png

其.png


public:公共的,后期会讲

static:静态的

void:无返回值

形参可以为空,要是有形参,必须得传实参。要是有多个形参,就得传多个实参,传的顺序一一对应,多个形参需要用逗号隔开

方法名采用小驼峰命名规范

在java当中,方法必须写在类当中

在java当中,没有方法声明

通过函数名(实参)进行调用

定义方法的时候, 不会执行方法的代码. 只有调用的时候才会执行

一个方法可以被多次调用

代码从主函数开始执行,主函数结束。当在主函数中执行到 isLeapYear(year) 这个代码时,我们就知道需要调用这个函数了,把 主函数中的 year 值 传给了形参中的  year(注:此形参非彼形参),然后执行这个函数,执行完后返回到主函数中继续执行主函数


方法的好处:


当下面的代码还要使用这个方法时,可以直接调用,不需要重复去写这些代码


方法调用过程:


调用方法--->传递参数--->找到方法地址--->执行被调方法的方法体--->被调方法结束返回--->回到主调方法继续往下执行


1.3 实参 和 形参 的关系

方法的形参相当于数学函数中的自变量, 比如:y = x + 1


形参就相当 x ,用来接收 实参 传过来的值。当传过来的实参值不一样时, y 最后的值也是不一样的


形参的名字可以随意取,对方法都没有任何影响,形参只是方法在定义时需要借助的一个变量,用来保存方法在调用时传递过来的值


public class Test {
    public static int gainX(int x) {
        return x + 1;
    }
    public static void main(String[] args) {
        System.out.println(gainX(100));
    }
}

x 就是一个 形参,用于接收实参的值,实参就是100,负责给形参传值


在Java中,实参的值永远都是拷贝到形参中,形参和实参本质是两个实体


证明形参和实参本质是两个实体:


public class Test {
    public static void swap(int x,int y) {
        System.out.println(x);
        System.out.println(y);
        int tmp = x;
        x = y;
        y =tmp;
        System.out.println(x);
        System.out.println(y);
    }
    public static void main(String[] args) {
        int a = 10;
        int b = 20;
        swap(a,b);
        System.out.println(a);
        System.out.println(b);
    }
}

运行结果:

请.png



a = 10,b = 20,然后调用swap方法,将 a 的值传给了形参 x ,将 b 的值传给了形参 y。然后执行swap 方法体,打印 x 和 y ,因为是将 a 和 b的值 传给了 x 和 y 所以打印的 x 是 10,y 是 20,然后交换 x 和 y 里面的值,然后在打印交换后的 x 和 y, x 是 20,y 是 10,执行完swap方法后,回到主函数继续执行主函数剩下的代码,打印 a 和 b ,因为 形参 和 实参 是两个独立的实体,形参的改变不影响实参,所以打印的 a 还是 10,b 还是 20


那怎么样才能让形参的改变同时也影响的实参了?


答:因为方法最多只能返回一个值,所以有时候不得不让形参的改变同时也影响着实参,解决办法就是传数组给形参。(大家目前只做了解,后期博文里面会讲)


1.4 有返回值的方法和没有返回值的方法

方法可以有返回值,也可以没有返回值。当没有返回值时,我们就把方法的返回类型写成 void 就表示无返回值


①有返回值的方法


public class Test {
    public static int summation(int n) {
        int sum = 0;
        for (int i = 1; i <= n; i++) {
            sum += i;
        }
        return sum;
    }
    public static void main(String[] args) {
        int a = 10;
        int sum = summation(a);
        System.out.println(sum);
    }
}

这个代码就是求1 ~ n 的和的代码,传一个值给 summation 这个方法它就将 1 到 这个值之间的所以数加起来,返回通过 return 返回一个int类型的值,我们用一个int类型的变量接收即可


②无返回值的方法


public class Test {
    public static void print(int n) {
        if (n >= 10) {
            System.out.println("大于等于10");
        } else {
            System.out.println("小于10");
        }
    }
    public static void main(String[] args) {
        int a = 10;
        print(a);
    }
}

这个代码就是判断一个数是否大于等于10或者小于10,传一个数给 print 方法它自动判断,然后直接打印,不会返回任何结果  

2.方法重载

2.1 为什么需要方法重载

假设我们有一个方法是专门用来求两个数的和,那它的形参类型我们应该设置为什么?


答: 如果设置为 整型,就不能处理浮点型了,设置为浮点型就不能处理整型了,所以我们通常会写功能一样但是形参类型不一样的方法,这样就可以处理不同类型变量了。这样就会面对这样一个问题,功能一样,形参类型不一样,那如果其中一个方法名叫 sum,那另一个方法名叫什么咧?所以就有了方法重载


2.2 方法重载的概念

方法重载:如果多个方法的名字相同,参数列表不同,则称该几种方法被重载了


方法重载的好处:当一些方法功能一样,但是形参列表不一样时,我们可以使用同一个方法名


public class Test {
    public static int sum(int num1,int num2) {
        return num1 + num2;
    }
    public static double sum(double num1,double num2) {
        return num1 + num2;
    }
    public static void main(String[] args) {
        int a = 10;
        int b = 20;
        int c = sum(a,b);
        System.out.println(c);
        double d = 2.1;
        double e = 1.5;
        double f = sum(d,e);
        System.out.println(f);
    }
}


上述代码中的两个 sum 方法就形成了重载


从上述代码中,我们可以了解方法重载的三要素:


方法名必须相同

参数列表必须不同(参数的个数不同、参数的类型不同、类型的次序必须不同)

与返回值类型是否相同无关

方法中不能定义两个名字一样的变量,那为什么类中就可以定义方法名相同的方法呢?


答:因为方法是要经过方法签名的(经过编译器编译修改过之后方法最终的名字),具体方式:方法全路径名+参数列表+返回值类型,构成方法完整的名字。所以参数列表不同,最后构成的方法完整名字也是不同的


3.递归

3.1递归的概念

递归 顾名思义 递 反复执行一个方法,当条件不满足时就得 归 了


举例:


从前有坐山,山上有座庙,庙里有个老和尚给小和尚将故事,讲的就是:


从前有座山,山上有座庙,庙里有个老和尚给小和尚讲故事,讲的就是:


"从前有座山,山上有座庙..."


那么 这个故事结束的条件就是老和尚睡着或者小和尚睡着


上面故事中的特征就是自身中又包含了自己


递归:一个方法在执行的过程中调用自身,就称为“递归”


递归必要的条件:


原问题中必须包含子问题(注意:子问题的解法必须和原问题的解法一样)  

递归出口

我们遇到的问题直接并不好解决,但是发现将原问题拆分成其子问题之后,子问题与原问题有相同的解法,等子问题解 决之后,原问题就迎刃而解了


public class Test {
    public static int fac(int n) {
        if (n == 1) {
            return 1;
        } else {
            return n * fac(n - 1);
        }
    }
    public static void main(String[] args) {
        int n = 3;
        int ret = fac(n);
        System.out.println(ret);
    }
}


上述代码就是就求 n 的阶乘的问题,这个代码的 fac 方法就用了递归的思想。


去.png


关于 "调用栈"


方法调用的时候, 会有一个 "栈" 这样的内存空间描述当前的调用关系. 称为调用栈.

每一次的方法调用就称为一个 "栈帧", 每个栈帧中包含了这次调用的参数是哪些, 返回到哪里继续执行等信息

注:要是递归次数太多就会造成栈溢出, 那么就应该采用迭代


注:递归一定要有出口,否则会造成栈溢出  



相关文章
|
17天前
|
存储 Java 程序员
Java基础的灵魂——Object类方法详解(社招面试不踩坑)
本文介绍了Java中`Object`类的几个重要方法,包括`toString`、`equals`、`hashCode`、`finalize`、`clone`、`getClass`、`notify`和`wait`。这些方法是面试中的常考点,掌握它们有助于理解Java对象的行为和实现多线程编程。作者通过具体示例和应用场景,详细解析了每个方法的作用和重写技巧,帮助读者更好地应对面试和技术开发。
58 4
|
28天前
|
Java API
Java 对象释放与 finalize 方法
关于 Java 对象释放的疑惑解答,以及 finalize 方法的相关知识。
46 17
|
21天前
|
Java 测试技术 Maven
Java一分钟之-PowerMock:静态方法与私有方法测试
通过本文的详细介绍,您可以使用PowerMock轻松地测试Java代码中的静态方法和私有方法。PowerMock通过扩展Mockito,提供了强大的功能,帮助开发者在复杂的测试场景中保持高效和准确的单元测试。希望本文对您的Java单元测试有所帮助。
63 2
|
1月前
|
算法 Java Linux
java制作海报二:java使用Graphics2D 在图片上合成另一个照片,并将照片切割成头像,头像切割成圆形方法详解
这篇文章介绍了如何使用Java的Graphics2D类在图片上合成另一个照片,并将照片切割成圆形头像的方法。
49 1
java制作海报二:java使用Graphics2D 在图片上合成另一个照片,并将照片切割成头像,头像切割成圆形方法详解
|
29天前
|
Java 开发者
在Java多线程编程中,创建线程的方法有两种:继承Thread类和实现Runnable接口
【10月更文挑战第20天】在Java多线程编程中,创建线程的方法有两种:继承Thread类和实现Runnable接口。本文揭示了这两种方式的微妙差异和潜在陷阱,帮助你更好地理解和选择适合项目需求的线程创建方式。
19 3
|
1月前
|
Java 大数据 API
别死脑筋,赶紧学起来!Java之Steam() API 常用方法使用,让开发简单起来!
分享Java Stream API的常用方法,让开发更简单。涵盖filter、map、sorted等操作,提高代码效率与可读性。关注公众号,了解更多技术内容。
|
29天前
|
Java 开发者
在Java多线程编程中,选择合适的线程创建方法至关重要
【10月更文挑战第20天】在Java多线程编程中,选择合适的线程创建方法至关重要。本文通过案例分析,探讨了继承Thread类和实现Runnable接口两种方法的优缺点及适用场景,帮助开发者做出明智的选择。
18 2
|
29天前
|
安全 Java
Java多线程通信新解:本文通过生产者-消费者模型案例,深入解析wait()、notify()、notifyAll()方法的实用技巧
【10月更文挑战第20天】Java多线程通信新解:本文通过生产者-消费者模型案例,深入解析wait()、notify()、notifyAll()方法的实用技巧,包括避免在循环外调用wait()、优先使用notifyAll()、确保线程安全及处理InterruptedException等,帮助读者更好地掌握这些方法的应用。
18 1
|
29天前
|
Java 开发者
Java多线程初学者指南:介绍通过继承Thread类与实现Runnable接口两种方式创建线程的方法及其优缺点
【10月更文挑战第20天】Java多线程初学者指南:介绍通过继承Thread类与实现Runnable接口两种方式创建线程的方法及其优缺点,重点解析为何实现Runnable接口更具灵活性、资源共享及易于管理的优势。
34 1
|
29天前
|
Java
在Java多线程编程中,`wait()`和`notify()`方法的相遇如同一场奇妙的邂逅
在Java多线程编程中,`wait()`和`notify()`方法的相遇如同一场奇妙的邂逅。它们用于线程间通信,使线程能够协作完成任务。通过这些方法,生产者和消费者线程可以高效地管理共享资源,确保程序的有序运行。正确使用这些方法需要遵循同步规则,避免虚假唤醒等问题。示例代码展示了如何在生产者-消费者模型中使用`wait()`和`notify()`。
27 1
下一篇
无影云桌面