java入门基础四(方法和数组)

8.方法

方法简述:

概念:特定功能的代码块。

优点:减少了代码的冗余。

方法的分类:静态方法、成员方法、构造方法(此节主要在静态方法的基础上使用)

注意:

  1. 方法编写的位置:类里,与main方法并立。
  2. 方法与方法之间是平级关系(不能在一个方法中声明另一个方法)。
  3. 方法不被调用,永远不会主动执行。

8.1 静态方法(static)

注:只能使用类名调用,无法使用类对象调用。

8.1.1 无返回值无参数的方法

语法结构:

​ 访问修饰符 static void 方法名(){
​ …代码块…

​ }

示例:

public static void hello(){
	System.out.println("Hello World!");			
}

在main方法中可以直接通过方法名调用------ hello();

8.1.2.带有参数的方法

语法结构:

访问修饰符 static void 方法名(参数类型 变量名){
…代码块…
}

示例:

public static void printStar(int num,String str){
	for(int i = 0;i<num;i++){
		for(int j = 0;j<=i;j++){
			System.out.print(str);
		}
		System.out.println();
	}
}

main()方法中调用printStar方法时,需要传递实参给printStar方法。

printStar(5,"*")

输出:

*
**
***
****
*****

注意:

  1. 形参:形式参数,方法声明时,规定调用时要传入的数据类型及接收数据的变量
  2. 实参:实际参数,调用方法时传入的具体数据
  3. 实参与形参类型必须兼容
  4. 多个参数用逗号分隔

8.1.3.带有返回值的方法

语法结构:

public static 返回值类型 方法名([参数]){
…代码块…
return 返回数据;
}

示例:

//计算两个int类型的和。
public static int add(int a,int b){
	int result = a+b;
	return result;//返回具体参数
}

注意:

  1. return下面不能接执行语句,因为return表示结束当前方法(如果存在分支,不是每个分支都存在return时,主干函数必须需要一个return语句。)。
  2. 声明方法时规定返回值类型,return后面接的是要返回的具体数据,返回的数据类型和定的返回值类型必须兼容。
  3. 方法中的变量为局部变量,作用域在该方法内,不影响其他方法中的变量。

8.1.4.方法的重载

含义:方法与方法之间的关系
好处:系统会根据实参类型自动匹配到对应方法
条件:
1.在同一个类里
2.方法名一致
3.参数列表的个数或者类型不一致
4.与访问修饰符,返回值无关
应用场景:
在同一个类里,有多个方法功能一致,细节实现不一样,就可以考虑使用重载(例如:多个整数求最大值。)

示例:

public static void main(String[] args){				
	
    System.out.println(getMax(10,20));
    System.out.println(getMax(10,20,30,40));

}


public static int getMax(int a,int b){
	return (a>b)?a:b;
}	

public static int getMax(int a,int b,int c){
	int max = getMax(a,b);
	max = getMax(max,c);
	return max;
}
	
public static int getMax(int a,int b,int c,int d){
	int max = getMax(a,b);
	max = getMax(max,c);
	max = getMax(max,d);
	return max;
}
/*
20
40
*/

8.1.5 递归的使用

概念:方法调用方法自身。

要点:

  1. 找规律(找出联系)。
  2. 找出口(结束的标志)。

示例:

Fibonacci 数列: 0, 1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89, 144,

找出规律和联系: a1=1,a2=1,an=a(n-1)+a(n-2)(n>=3,n∈N*)

找出结束的标志: a1=1,a2=1

public static void main(String[] args){				
	
    System.out.println(fibonacci(10));

}

public static int fibonacci(int n){
	if(n==1 || n==2){
		return 1;
	}else{
		return fibonacci(n-1) + fibonacci(n-2);
	}
}
/*
输出结果:
55
*/

注意:

​ 方法没有出口就会导致死循环,直到栈内存溢出报错(调用方法时,会在栈内存中开辟空间,用于存放该方法的局部变量,死循环的调用方法,栈内存就会满载并溢出)。

8.1 成员方法

含义:表示对象所具有的功能。

作用:

​ 调用时与静态方法不同,需要使用类的对象来调用。

​ 对象可以多次调用成员函数,

​ 可以有返回值,也可以为void类型。

​ 方法名可以和类名相同,但当此成员函数没有返回类型时为构造函数。

8.2 构造方法

  1. 格式:

    构造方法和类名相同,并且没有返回类型和返回值。

    一个类可以有多个构造函数,但要求他们满足方法的重载。

    构造函数与其他方法一样可以有0个、1个、或多个参数。

  2. 作用:

    构造方法在创建对象时被调用,一个对象的建立只能调用一个构造函数,可用于初始化对象。

注:编译程序如果类中没有构造函数,系统会自动加入构造函数,为此类的默认构造函数。

8.3 main方法

  1. 格式:
public static void main(String[] args) {
    //代码块
}
  1. 含义:

​ 在Java中,main()方法是Java应用程序的入口方法,也就是说,程序在运行的时候,第一个执行的方法就是main()方法。

这个方法和其他的方法有很大的不同,比如方法的名字必须是main,方法必须是public static void 类型的,方法必须接收一个字符串数组的参数。

  1. main方法中的args参数:

    ​ main方法中还有一个输入参数,类型为String[],这个是java的规范,main()方法中必须有一个入参,类型必须String[],命名为args,则是多数人的习惯。

    使用示例:

    public static void main(String[] args){
        
    	for(String str : args){
    		System.out.println(str);
    	}
    }
    

    编译过程:
    在这里插入图片描述

拓展:

由于JVM在运行这个Java应用程序的时候,首先会调用main方法,调用时不会实例化这个类的对象,而是通过类名直接调用因此main方法需要是限制为public static。(类名.main()) ,且不能有返回值,所以返回类型为void。

9. 数组

9.1一维数组

概念:一组数据的容器(数组可以存放多个数据)

注意:

​ 1.数组是引用数据类型
​ 2.数组中的数据又叫做元素
​ 3.每个元素都有编号叫做下标/索引(index)
​ 4.下标从0开始
​ 5.数组初始化后,会在内存中开辟一连串连续的空间
​ 6.数组一旦初始化后长度不可以改变(数组没有扩容和删除)
​ 7.数组的操作:添加、修改、查询

声明: 数据类型[] 数组名;

在这里插入图片描述

9.1.1 静态初始化

数据由程序员指定,长度由系统分配。

静态初始化的三种方式:

示例:

//静态初始化1
String[] str1 = new String[]{"a111","a222","a333","a444"};	
//静态初始化2
String[] str2;
str2 = new String[]{"b111","b222","b333","b444"};	
//静态初始化3
String[] str3 = {"c111","c222","c333","c444"};

9.1.2 动态初始化

数据由系统指定,长度由程序员分配。

注:

默认指定类型:

​ 整数类型:0
​ 浮点类型:0.0
​ 字符类型:’ ’
​ 布尔类型:false
​ 引用类型:null

示例:

//动态初始化
String [] str =new String[5];
//赋值
str[0]="111";
str[1]="222";
str[2]="333";
str[3]="444";
str[4]="555";

动态初始化和静态初始化:

一开始就知道数据,采用静态初始化,反之,只知道数据长度(个数)就采用动态初始化。

9.1.3 数组相关操作

9.1.3.1 获取和修改数组内容
  1. 通过索引能够指定获取数组元素和修改数组元素。

示例(参照动态初始化化的str):

System.out.println(str[2]);//333
String a="dididi";
str[2]=a;
System.out.println(str[2]);//dididi
/*
输出结果:
333
dididi
*/
  1. 通过length获取数组元素个数。

    int len = str.length;
    System.out.println(len);
    /*
    5
    */
    
  2. for循环遍历

    for(int i = 0;i<str.length;i++){
    	System.out.println(str[i]);
    }
    /*
    111
    222
    dididi
    444
    555
    */
    
  3. 增强for循环遍历(foreach)

    for(String s:str){
    	System.out.println(s);
    }
    /*
    111
    222
    dididi
    444
    555
    */
    

注:

​ 遍历是如果需要使用下标,通过for循环遍历,如果不需要使用下标就采用foreach遍历数组。

9.1.3.2 数组的排序(数值型)

冒泡排序:

int[] num = {2,7,5,4,8,6};
		
for(int i = 0;i<num.length-1;i++){
	for(int j = 0;j<num.length-1-i;j++){
		if(num[j] > num[j+1]){
			int temp = num[j];
			num[j] = num[j+1];
			num[j+1] = temp;
		}
	}
}

使用Arrays工具类方法排序(后续9.1.6详细介绍Arrays工具类)

//导包
import java.util.Arrays;
//使用
Arrays.sort(num);
9.1.3.3 数组的查找
  1. 顺序查找(遍历查找)

    for(int i = 0;i<num.length;i++){
    	if(num[i] == numbers){
    		System.out.println("查找到了");
    	}
    }
    
  2. 二分法查找(使用对象:有序的数组)

    int start = 0;             //数组首端
    int end = num.length-1;	   //数组末端
    int numbers=7//查询目标
    while(start <= end){
    	int mid = (start+end)/2;		
    	if(numbers >num[mid]){
    		start = mid+1;
    	}else if(numbers < num[mid]){
    		end = mid-1;
    	}else{
    		System.out.println("查找到了");
    		break;
    	}
    }
    
9.1.3.4 数组的扩充
String [] names={"aa","bb","cc"}; //静态初始化数组。
int  capacity = names.length + (names.length<<1); //拓展容量(增加原来的2倍)
String [] newNames = new String [capacity];
//复制数据
for(int i = 0;i<names.length;i++){
	newNames[i] = names[i];
}
names= newNames;  //将扩充之后的数组给原数组。
for (String string : newNames) {
	System.out.println(string);
}
/*
aa
bb
cc
null
null
null
null
null
null
*/
9.1.3.5 数组的复制
  1. 直接复制。

    String [] names = {"11","22","33","55"};  //准备复制的原字符数组
    String [] newNames = names;               //新的字符数组
    for(String str : newNames){				  //遍历
    	System.out.print(str+" ");
    }
    System.out.println();
    names[2]="aa";                            //将原字符数组改变。
    for(String str : newNames){				  //遍历
    	System.out.print(str+" ");
    	}
    }
    /*
    输出结果:
    11 22 33 55 
    11 22 aa 55 
    */
    

    注意:当采用这种方式复制字符数组时,修改原数组,新的数组内容也随之改变。(当names赋值给newNames时,只是将字符数组的地址传递给新数组,所以两个数组操作的其实是一片空间。)

  2. 只复制内容。

    当复制一个数组只是为了获取其中的数据时,就可以采取动态初始化,对新建的字符数组单个赋值,从而避免了多个数组操作同样的一组数据。

    String [] names = {"11","22","33","55"};  //准备复制的原字符数组
    String [] newNames =new String[names.length]; 
    for(int i = 0;i<names.length;i++){
    	newNames[i] = names[i];
    }
    for(String str : newNames){					   //遍历
    	System.out.print(str+" ");
    }
    names[2]="aa";
    System.out.println();
    for(String str : newNames){					   //遍历
    	System.out.print(str+" ");
    }
    /*
    输出结果:
    11 22 33 55 
    11 22 33 55 
    */
    

    原数组的变化,不会对新数组产生影响。

9.1.3.6 删除数组内容
  1. 数据外部迁移(将需要删除的数据舍弃,获得新数组。)

    String [] names ={"11","22","33","44"};   //需要删除的数据为22
    String [] newNames =new String[names.length-1];
    int index=0;                         //新数组的索引,从0开始
    for (String string : names) {
    	if(!string.equals("22")){
    	newNames[index++]=string;
    	}
    }		
    names = newNames;                           //将新数组的地址赋值给源数组
    for (String string : names) {
    	System.out.println(string);
    	}
    }
    /*
    输出结果:
    11
    33
    44
    */
    

    注:这种方法会使原本的数组空间减小

  2. 数据内部迁移(在数组内部将需要删除的数据覆盖。)

    String [] names ={"11","22","33","44"};   //需要删除的数据为22
    //"22"的索引为1,for循环从1开始,直到names.length-1结束。		
    for (int i = 1; i < names.length-1; i++) {
    	names[i]=names[i+1];			
    }
    //删除一个数据后,依次向前覆盖,数组最后一位置为空。
    names[names.length-1]=null;
    for (String string : names) {
    	System.out.println(string);
    	}
    }
    /*
    输出结果:
    11
    33
    44
    null
    */
    

    注:数组的长度不会经历变化。

9.1.4 数组作为参数和返回值

示例:长传一组数据,返回最大值和最小值。

public static void main(String[] args) {
	int [] num={1,2,3,4,5};   //采用静态初始化
	int [] get = getMaxMin(num);
	System.out.println("最小值为:"+get[0]+"    最大值为:"+get[1]);
	
}
public static int [] getMaxMin(int [] num){
	int min  = num[0];
	int max = num[0];
	for (int i = 0; i < num.length; i++) {
		if(min>num[i])min=num[i];
		if(max<num[i])max=num[i];
	}
	return new int[]{min,max};
}
/*
输出结果:
最小值为:1    最大值为:5
*/

9.1.5 可变参数

示例:设计方法,传入任意个int值,求和。

public static void main(String[] args) {
	int sum=add(1,2,3,4,5,6);
	int sum1=add(1,2,3,4,5);
	System.out.println(sum);
	System.out.println(sum1);
}
public static int add(int...is){         //求和函数
	int sum =0;
	for (int i : is) {                   //遍历相加
		sum+=i;
	}
	return sum;
}
/*
输出结果:
21
15
*/

由此可见:可变参数的底层就是数组。

注意:

  1. 可变参数后不能接其他参数,但之前可以。

    例:

    public static void method(int a,String... ss)
    
  2. 一个方法的参数中,不能同时出现两个可变参数(即便类型不同)。

9.1.6 Arrays工具类

Arrays: java 给我们提供的专门操作数组的工具类。(其中的方法定义和使用详见API-----java类使用说明书)

常见示例:

int[] is = {39,77,27,20,45,62};
//由小到大排序
Arrays.sort(is);  //20 27 39 45 62 77

//查找1(含有查找的元素)
int index =  Arrays.binarySearch(is,45);
System.out.println("查找元素的下标为:" + index);  //查找元素的下标为:3

//查找2(未含有查找的元素)
int index =  Arrays.binarySearch(is,42);
System.out.println("查找元素的下标为:" + index); //查找元素的下标为:-4
/*
	注:binarySearch方法,如果元素在数组中就返回下标,否则返回 (-插入点)-1
*/
//替换
Arrays.fill(is,100);     //100 100 100 100 100 100 
Arrays.fill(is,1,4,666); //100 666 666 666 100 100 
		
//拷贝
int[] copyOf = Arrays.copyOf(is,is.length*2);
for ( int i : copyOf) {
	System.out.print(i+" ");  //100 666 666 666 100 100 0 0 0 0 0 0 
}
int[] copyOfRange = Arrays.copyOfRange(is,3,8);
for (int i : copyOfRange) {
	System.out.print(i+" "); //666 100 100 0 0 
}

9.2 二维数组

注:二维数组整体学习和一维数组类似,可参照学习。

含义:包含了多个一维数组

声明:数据类型 [ ] [ ] 数组名;

9.2.1 二维数组的初始化

  1. 静态初始化:数据由程序员指定,长度由系统自动分配

    //方式1
    String [][] names1=new String [][] {{"aaa","bbb","ccc"},{"111","222","333","444"}};
    
    //方式2
    String [][] names2;
    names2 = new String [][] {{"aaa","bbb","ccc"},{"111","222","333","444"}};
    
    //方式3
    String [][] names3={{"aaa","bbb","ccc"},{"111","222","333","444"}};
    
  2. 动态初始化:长度由程序员指定,数据由系统自动分配(默认分配方式见9.1.2)

    //动态初始化1
    String[][] names1 = new String[2][3];// 含义:2个一维数组,每个一维数组中有3个元素
    
    //动态初始化2
    String[][] names2;
    names = new String[2][3];
    
    //动态初始化3
    String[][] names3 = new String[2][];//含义:标注二维数组中有2个一维数组
    //把长度为3的一维数组赋值给二维数组中下标为0的位置
    names3[0] = new String[3];
    //把长度为4的一维数组赋值给二维数组中下标为1的位置
    names3[1] = new String[4];
    
  3. 二维数组的循环遍历(采用循环嵌套)

    String [][] names={{"aaa","bbb","ccc"},{"111","222","333","444"}};//静态初始化
    
    
    //遍历 - for循环
    for (int i = 0; i < names.length; i++) {
    	for (int j = 0; j < names[i].length; j++) {
    		System.out.print(names[i][j]);
    	}
        System.out.println();
        
    }		
    System.out.println("------------");		
    //遍历 - foreach
    for (String[] strings : names) {
    	for (String string : strings) {
    		System.out.print(string);
    	}
        System.out.println();
    }
    /*
    aaabbbccc
    111222333444
    ------------
    aaabbbccc
    111222333444
    */
    
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值