字节跳动线上笔试:字符串路径匹配

题目描述: 输入一个二维字符数组map和一个字符串数组word,判断word中的元素是否在map中有相应的路径存在,其中map中的路径可以上下左右各走一格。如果存在输出 Has,如果不存在输出 Not Has。

像Word中的第一行在Map中第一列存在,Word中的第二行在Map中的第三行存在,....

解题思路:本题使用回溯法,深度优先搜素遍历二维字符数组中的元素,寻找可能存在的路径。

代码如下:

public class Test {
	
	public static void main(String[] args) {

        Scanner sc = new Scanner(System.in);
        System.out.println("请输入map的行数:");
        int n = sc.nextInt();
        System.out.println("请输入map的列数:");
        int m = sc.nextInt();
        System.out.println("请输入word的行数:");
        int q = sc.nextInt();
        System.out.println("请输入map的元素:");
        char[][] map = new char[n][m];
        for(int i = 0; i < n; i++) {
            String s = sc.next();
            char[] c = s.toCharArray();
        	map[i] = c;
        }
        System.out.println("请输入word的元素: ");
        String[] word = new String[q];
        for(int i =0; i < q; i++) {
        	word[i] = sc.next();
        }
        
		CheckString(map, n, m, word);
		
	}
	
	//检查字符数组中是否有指定的字符串路径
	public static void CheckString(char[][] map, int n, int m, String[] word){	
		//分别取字符串数组中的每个字符串
		for(int i=0;i<word.length;i++) {
			//将字符串转换为一维char字符数组
			char[] ch = word[i].toCharArray();
			Check(map,n,m,ch,i);		
		}		
	}
	//
	public static void Check(char[][]map, int n, int m, char[]ch,int flag){ 
		//定义一维访问矩阵,记录每次二维字符数组中字符是否被访问
		boolean[] visited = new boolean[n*m];
		//初始化访问矩阵
		for(int i=0;i<n;i++) {
			for(int j=0;j<m;j++) {
				visited[i*m+j] =false;
			}
		}	
		boolean has = false;
		//遍历二维数组中的所有元素
		out:for(int i=0;i<n;i++) {
			for(int j=0;j<m;j++) {
				has = CheckVisited(map, i, j, n, m, ch, 0, flag, visited);
				if(has)
					break out;
			}
		}
		if(has) {
			System.out.println("case: " + flag + "  Has");
		}else {
			System.out.println("case: " + flag + "  Not Has");
		}	
	}
	//如果二维数组中存在匹配字符串的路径,则返回true,否则返回false
	public static boolean CheckVisited(char[][]map, int a, int b, int n, int m, char[]ch, int i,int flag, boolean[]visited) {
		//递归调用的约束条件
		if(a>=0&&b>=0&&a<n&&b<m&&!visited[a*m+b]&&i<ch.length&&ch[i]==map[a][b]) {
			i++;
			visited[a*n+b]=true;
			return CheckVisited(map,a,b-1,n,m,ch,i,flag,visited)||CheckVisited(map,a+1,b,n,m,ch,i,flag,visited)
				   ||CheckVisited(map,a,b+1,n,m,ch,i,flag,visited)||CheckVisited(map,a-1,b,n,m,ch,i,flag,visited);	
		}
	    if(i==ch.length-1) {
	    	return true;
	    }
	    return false;
	}	
}

运行结果:

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值