Recursividad
1. Concepto: Invoquese a sí mismo
Caso: Requisitos: ¡Cuente 5!
Método 1: Utilice el bucle for
int result=1;
for (int i = 1; i <=5; i++) {
result=result*i;
}
System.out.println(result);
}
Método dos: usa la recursividad
public static int fun(int num) {
if (num ==1) {
return 1;
}else {
return num*fun(num-1);
}
}
Desventajas: La recursividad no se puede llamar demasiadas veces, de lo contrario, la memoria de pila se desbordará.
beneficio: No es necesario conocer el número de ciclos
problema: El
constructor no puede utilizar llamadas recursivas. Una llamada recursiva puede tener un valor de retorno o ningún valor de retorno.
Ejercicios recursivos (1)
Requisitos: Ingrese una ruta de carpeta desde el teclado e imprima todos los nombres de archivo .java en la carpeta
Análisis:
1. Obtenga todos los archivos y carpetas en la ruta de la carpeta y guárdelos en la matriz de archivos
2. Recorre la matriz y juzga cada archivo o carpeta.
3. Si es un archivo y el sufijo es .java, imprímalo
4. Si es una carpeta, llámala recursivamente
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);
}
}
}
}
El efecto es el siguiente:
Ejercicios recursivos (2)
Requisito: Reciba una ruta de carpeta desde el teclado y cuente el tamaño de la carpeta.
Análisis:
Reciba una ruta de carpeta desde el teclado
- Crear objetos de entrada de teclado
- Definir un bucle inalámbrico
- Almacene y encapsule los resultados de la entrada del teclado en objetos de archivo
- Juzgar el objeto Archivo
- Devolver objeto de ruta de carpeta
Cuente el tamaño de la carpeta
- Definir una variable de suma
- Obtenga todos los archivos y carpetas en esta carpeta ListFiles ();
- Atraviesa la matriz
- Si es un archivo, calcula el tamaño y súmalo
- Juzga que es una carpeta, llama de forma recursiva
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;
}
}
El efecto es el siguiente:
Ejercicios recursivos (3)
Requisitos: ingrese la ruta desde la consola y elimine la carpeta
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;
}
}
}
}
Ejercicios recursivos (4)
Requisito: Reciba dos rutas de carpeta desde el teclado y copie una de las carpetas (con contenido) a otra carpeta.
Análisis:
- Crea la carpeta original en la carpeta de destino
- Obtenga todos los archivos y carpetas en la carpeta original y guárdelos en la matriz de archivos
- Atraviesa la matriz
- Si es un archivo, use io stream para leer y escribir
- Si es una carpeta, llámala recursivamente
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;
}
}
}
}
Ejercicios recursivos (5)
Requisito: imprimir por nivel, recibir una ruta de carpeta desde el teclado, imprimir todos los archivos en la carpeta y el nombre de la carpeta por nivel, por ejemplo:
aaa es una carpeta, hay bbb.txt, ccc.txt, ddd.txt en ella Estos archivos, hay carpetas como eee, fff.txt y ggg.txt en eee, imprima la jerarquía
Análisis:
1. Obtenga todos los archivos y carpetas, y la matriz de archivos devuelta
2. Atraviesa la matriz
3. Ya sea un archivo o una carpeta, debe imprimirse directamente
4. Si es una carpeta, llama de forma recursiva
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;
}
}
}
}
Al considerar este tipo de problema, debe considerar el problema de apilamiento
Ejercicios recursivos (6)
Requisito: secuencia de Fibonacci
El significado de la secuencia es que la suma de los dos elementos anteriores es igual al elemento actual. 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);
}
}
}
Joseph anillo
Demanda: buscando números de la suerte
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);
}
}