JAVA基础练习——递归,获取文件夹下所有文件,删除某个文件,文件拷贝,层级打印,斐波那契数列,约瑟夫环

递归

一、概念:自己调用自己
案例:需求:算5!
方法一:使用for循环

int result=1;
		for (int i = 1; i <=5; i++) {
			result=result*i;
		}
		System.out.println(result);
	}

方法二:使用递归

public static int fun(int num) {
		if (num ==1) {
			return 1;
		}else {
			return num*fun(num-1);
		}
	}

弊端:递归不能调用次数过多,否则栈内存溢出。
好处:不用知道循环次数
问题
构造方法不能使用递归调用。递归调用可以有返回值也可以没有返回值。

递归练习(一)

需求:从键盘输入接收一个文件夹路径,打印出该文件夹下所有的.java文件名
分析:
1. 获取到该文件夹路径下的所有的文件和文件夹,存储在File数组中
2. 遍历数组,对每一个文件或文件夹做判断。
3. 如果是文件,并且后缀是.java就打印
4. 如果是文件夹就递归调用

public class Demo1_Test {

	public static void main(String[] args) {
		File dir =getDir();
		printJavaFile(dir);
	}
	public static File getDir() {
		Scanner scanner =new Scanner(System.in);
		System.out.println("请输入一个文件夹路径:");
		while (true) {
			String line =scanner.nextLine();
			File dir =new File(line);
			if (!dir.exists()) {
				System.out.println("您录入的文件夹路径不存在,请重新录入");
			}else if (dir.isFile()) {
				System.out.println("您录入的是文件夹路径,请重新录入文件路径");
			}else {
				return dir;
			}
		}
	}
	
	//获取文件夹路径下的所有.java文件
	//返回值类型void
	//参数列表File dir
	public static void printJavaFile(File dir) {
		//获取到该文件路径下的所有的文件和文件夹,存储在File数组中
		File[] subFiles =dir.listFiles();
		//遍历数组,对每一个文件或文件夹做判断
		for (File subFile :subFiles) {
			//如果是文件,并且后缀名是.java的就打印
			if (subFile.isFile()&&subFile.getName().endsWith(".java")) {
				System.out.println(subFile);
			//如果是文件夹,就递归调用
			}else if (subFile.isDirectory()) {
				printJavaFile(subFile);
			}
				
			
		}
	}
}

效果如下:
在这里插入图片描述

递归练习(二)

需求:从键盘接收一个文件夹路径,统计该文件夹大小
分析:
从键盘接受一个文件夹路径

  1. 创建键盘录入对象
  2. 定义一个无线循环
  3. 将键盘录入的结果存储并封装成File对象
  4. 对File对象判断
  5. 将文件夹路径对象返回

统计该文件夹大小

  1. 定义一个求和变量
  2. 获取该文件夹下所有的文件和文件夹ListFiles();
  3. 对数组进行遍历
  4. 判断是文件就计算大小并累加
  5. 判断是文件夹,递归调用
public class Demo2_Test {

	public static void main(String[] args) {
		//File dir =new File("d:\\day15");
		//System.out.println(dir.length());//直接获取文件夹的结果是0
		File dir =getFile();
		System.out.println(getFileLength(dir));
	}
	
	public static File getFile() {
		Scanner scanner =new Scanner(System.in);
		System.out.println("请输入一个文件夹路径");
		while (true) {
			String line =scanner.nextLine();
			File dir = new File(line);
			//对File对象进行判断
			if (!dir.exists()) {
				System.out.println("文件路径不存在!");
			}else if(dir.isFile()) {
				System.out.println("这是文件夹路径,请输入文件路径");
			}
			else {
				//将文件夹路径对象返回
				return dir;
			}
		}	
	}
	//统计文件大小。返回值类型long,参数列表File dir
	public static long getFileLength(File dir) {
		//定义一个求和变量
		long len =0;
		//获取该文件夹下所有的文件和文件夹ListFiles
		File [] subFiles =dir.listFiles();
		//遍历数组
		for (File subFile : subFiles) {
			//判断如果是文件就计算大小并累加
			if (subFile.isFile()) {
				len +=subFile.length();
			}else {
				//如果是文件夹的话就在继续递归调用
				len+=getFileLength(subFile);
			}
			
		}
		return len;
	}
	
}

效果如下:
在这里插入图片描述

递归练习(三)

需求:从控制台输入路径,删除该文件夹

public class Demo3_Test {

	public static void main(String[] args) {
		File file =getFile();
		deleteFile(file);
	}
	
	//删除文件夹
	public static void deleteFile(File dir) {
		File[]subFiles=dir.listFiles();
		//遍历数组
		for (File subFile : subFiles) {
			if (subFile.isFile()) {
				//如果是文件夹就直接删除
				subFile.delete();
			}else {
				deleteFile(subFile);
			}
			
		}
		//循环结束后,把空文件夹删掉
		dir.delete();
	}
	
	public static File getFile() {
		Scanner scanner =new Scanner(System.in);
		System.out.println("请输入一个文件路径名称");
		while (true) {
			String line =scanner.nextLine();
			File dir =new File(line);
			if (!dir.exists()) {
				System.out.println("文件路径不存在或输入有误");
			}else if(dir.isFile()){
				System.out.println("这是文件夹路径,请输入文件路径");
			}else {
				return dir;
			}
		}
	}
}

递归练习(四)

需求:从键盘接收两个文件夹路径,把其中一个文件夹中(包含内容)拷贝到另一个文件夹中
分析:

  1. 在目标文件夹中创建原文件夹
  2. 获取原文件夹中所有的文件和文件夹,存储在File数组中
  3. 遍历数组
  4. 如果是文件就用io流读写
  5. 如果是文件夹就递归调用
public class Demo4_Test {

	public static void main(String[] args) throws IOException {
		File src =getFile();
		File desc =getFile();
		if (src.equals(desc)) {
			System.out.println("目标文件夹是原文件夹的子文件夹");
		}else {
			copy(src,desc);
		}
		
 
	}
	//把其中一个文件夹中(包含内容)拷贝到另一个文件夹中
	//返回值类型void
	//参数列表File src,File desc
	public  static void copy(File src, File desc) throws IOException {
	//在目标文件夹中创建原文件夹
		File newDir =new File(desc,src.getName());
		newDir.mkdir();
		//获取原文件夹中所有的文件和文件夹,存储在File数组中
		File[] subFiles =src.listFiles();
		for (File subFile : subFiles) {
			//如果是文件用io读写
			if (subFile.isFile()) {
				BufferedInputStream bis =new BufferedInputStream(new FileInputStream(subFile));
				BufferedOutputStream bos =
						new BufferedOutputStream(new FileOutputStream(new File(newDir,subFile.getName())));
				int b;
				while ((b=bis.read())!=-1) {
					bos.write(b);
				}
				bis.close();
				bos.close();
			}else {
				copy(subFile, newDir);
			}
			
		}
	}
	public static File getFile() {
		Scanner scanner =new Scanner(System.in);
		System.out.println("请输入一个文件路径");
		while (true) {
			String line =scanner.nextLine();
			File dir =new File(line);
			if (!dir.exists()) {
				System.out.println("文件路径不存在");
			}
			else if (dir.isFile()) {
				System.out.println("这是文件夹路径,请输入文件路径");
			}else {
				return dir;
			}
		}
	}
}

递归练习(五)

需求:按层级打印,从键盘接收一个文件夹路径,把文件夹中的所有文件以及文件夹的名字按层级打印, 例如:
aaa是文件夹,里面有bbb.txt,ccc.txt,ddd.txt这些文件,有eee这样的文件夹,eee中有fff.txt和ggg.txt,打印出层级来

分析:
1. 获取所有文件和文件夹,返回的File数组
2. 遍历数组
3. 无论是文件还是文件夹,都需要直接打印
4. 如果是文件夹,递归调用

public class Demo5_Test {

	public static void main(String[] args) {
		File dir =getFile();
		printLev(dir,0);

	} 
	public static void printLev(File dir ,int level) {
		//把文件夹中的文件和文件夹放入File数组中
		File[] subFiles =dir.listFiles();
		for (File subFile : subFiles) {
			for (int i = 0; i <=level; i++) {
				System.out.print("\t");
			}
			//不论是文件还是文件夹,都需要直接打印
			System.out.println(subFile);
			//如果是文件夹,递归调用
			if (subFile.isDirectory()) {
				printLev(subFile,level+1);
				//改变level++或者++level结果均不同
			}
		}
		
	}
	public static File getFile(){
		Scanner scanner =new Scanner(System.in);
		System.out.println("请输入一个文件路径");
		while (true) {
			String line =scanner.nextLine();
			File dir =new File(line);
			if (!dir.exists()) {
				System.out.println("输入的文件路径不存在");
			}else if (dir.isFile()) {
				System.out.println("请输入一个文件路径");
			}else {
				return dir;
			}
		}
	}
}

考虑该类问题一定要考虑进栈出栈问题

递归练习(六)

需求:斐波那契数列
用数列的意思就是前面两项相加等于当前项。an =an+1+an-2

public static int fun(int num) {
		if (num ==1 || num==2) {
			return 1;
		}else {
			return fun(num-2)+fun(num-1);
		}
	}
}

约瑟夫环

需求:寻找幸运数字

public class Demo8_Test {
public static void main(String[] args) {
	System.out.println(getLucklyNum(8));
}
public static int getLucklyNum(int num) {
	ArrayList<Integer> list =new ArrayList<Integer>();		//创建集合存储1到num的对象
	for (int i = 0; i < num; i++) {
		list.add(i);
	}
	int count =1;		//用于数数,只要是3的倍数就循环
	for (int i = 0;list.size()!=1; i++) {	//只要集合中人数超过1,就不断地删除
		if (i == list.size()) {
			i=0;							//重新归零
		}
		if (count%3==0) {					//如果是3的倍数就删除
			list.remove(i--);
		}
		count++;
	}
	return list.get(0);
}

}
  • 2
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值