您好,我们非常感谢您的帮助!
我需要创建一个程序,该程序通过一个从文件读取的char数组。然后,程序需要使用递归来查找与当前“ A”相邻(而非对角线)的“ A”的最长连续路径。它只能对每个“ A”计数一次,因此一旦到达路径的末尾就不能向后计数。我正在使用的示例char数组是:
8 13
EAADDOAN
ATAFAWOB
ADAAAAIA
AWUYAAAA
ZAWAADDX
AAAAAAAZ
IMBAQJAA
AIAINOAK
AZVAJAAQ
VPNKAAAJ
TAAAWKAW
AAAAHRAV
ETEMAALA
Length of the longest A path is 23
8表示列,而13表示数组的行。我已经设置了另一个布尔数组来跟踪是否已经计算了“ A”。下面是遍历每个位置并调用递归函数的方法(看起来有点奇怪,第一次在这里发布):
public int findLongestPathLength() {
// TODO Auto-generated method stub
int i, j, x, y;
int numOfAs = 0;
int longestPath = 0;
// Create boolean array for checking if an 'A' has been counted or not
alreadyCounted = new boolean[numOfArrays][arrLength];
// Initialize all values in alreadyCounted array to false
for(i = 0; i < numOfArrays; i++) {
for(j = 0; j < arrLength; j++ ) {
alreadyCounted[i][j] = false;
}
}
for(i = 0; i < numOfArrays; i++) {
for(j = 0; j < arrLength; j++ ) {
if(map[i][j] == 'A') {
alreadyCounted[i][j] = true;
numOfAs = findPathLengthRecursive(i, j) + 1;
/* If this iteration of finding the longest path of 'A's is the longest
so far, replace the longestPath value with this number of A's */
if(numOfAs > longestPath)
longestPath = numOfAs;
// Initialize all values in alreadyCounted array back to false
for(x = 0; x < numOfArrays - 1; x++) {
for(y = 0; y < arrLength - 1; y++ ) {
alreadyCounted[x][y] = false;
}
}
// Reset currentLength in findPathLengthRecursive back to 0
currentLength = 0;
}
}
}
return longestPath;
}
我创建的递归方法是: public int findPathLengthRecursive(int i,int j){ // TODO自动生成的方法存根
// To check if there is an 'A' to any of the sides of the current cell
boolean left = true, right = true, up = true, down = true;
/* Base case (when recursion should stop) is when there is no 'A's left to count in the path */
if(j == 0 || (j > 0 && (map[i][j - 1] != 'A' || alreadyCounted[i][j - 1]))){
left = false;
}
if(j == arrLength - 1 || (j < arrLength - 1 && (map[i][j + 1] != 'A' || alreadyCounted[i][j + 1]))) {
right = false;
}
if(i == numOfArrays - 1 || (i < numOfArrays - 1 && (map[i + 1][j] != 'A' || alreadyCounted[i + 1][j]))) {
down = false;
}
if(i == 0 || (i > 0 && (map[i - 1][j] != 'A' || alreadyCounted[i - 1][j]))) {
up = false;
}
// If there is no valid 'A's around then return currentLength
if(!left && !right && !down && !up) {
return currentLength;
} else {
if(down && left && up && right) {
alreadyCounted[i + 1][j] = true; // Show that this 'A' has already been counted
alreadyCounted[i][j - 1] = true; // Show that this 'A' has already been counted
alreadyCounted[i - 1][j] = true; // Show that this 'A' has already been counted
alreadyCounted[i][j + 1] = true; // Show that this 'A' has already been counted
currentLength += Math.max(Math.max(Math.max(findPathLengthRecursive(i + 1, j), findPathLengthRecursive(i, j - 1)), findPathLengthRecursive(i - 1, j)), findPathLengthRecursive(i, j + 1));
}
else if(left && up && right) {
alreadyCounted[i][j - 1] = true; // Show that this 'A' has already been counted
alreadyCounted[i - 1][j] = true; // Show that this 'A' has already been counted
alreadyCounted[i][j + 1] = true; // Show that this 'A' has already been counted
currentLength += Math.max(Math.max(findPathLengthRecursive(i, j - 1), findPathLengthRecursive(i - 1, j)), findPathLengthRecursive(i, j + 1));
}
else if(up && right && down) {
alreadyCounted[i - 1][j] = true; // Show that this 'A' has already been counted
alreadyCounted[i][j + 1] = true; // Show that this 'A' has already been counted
alreadyCounted[i + 1][j] = true; // Show that this 'A' has already been counted
currentLength += Math.max(Math.max(findPathLengthRecursive(i - 1, j), findPathLengthRecursive(i, j + 1)), findPathLengthRecursive(i + 1, j));
}
else if(right && down && left) {
alreadyCounted[i][j + 1] = true; // Show that this 'A' has already been counted
alreadyCounted[i + 1][j] = true; // Show that this 'A' has already been counted
alreadyCounted[i][j - 1] = true; // Show that this 'A' has already been counted
currentLength += Math.max(Math.max(findPathLengthRecursive(i, j + 1), findPathLengthRecursive(i + 1, j)), findPathLengthRecursive(i, j - 1));
}
else if(down && left && up) {
alreadyCounted[i + 1][j] = true; // Show that this 'A' has already been counted
alreadyCounted[i][j - 1] = true; // Show that this 'A' has already been counted
alreadyCounted[i - 1][j] = true; // Show that this 'A' has already been counted
currentLength += Math.max(Math.max(findPathLengthRecursive(i + 1, j), findPathLengthRecursive(i, j - 1)), findPathLengthRecursive(i - 1, j));
}
else if(left && right) {
alreadyCounted[i][j - 1] = true; // Show that this 'A' has already been counted
alreadyCounted[i][j + 1] = true; // Show that this 'A' has already been counted
currentLength += Math.max(findPathLengthRecursive(i, j - 1), findPathLengthRecursive(i, j + 1));
}
else if(up && down) {
alreadyCounted[i - 1][j] = true; // Show that this 'A' has already been counted
alreadyCounted[i + 1][j] = true; // Show that this 'A' has already been counted
currentLength += Math.max(findPathLengthRecursive(i - 1, j), findPathLengthRecursive(i + 1, j));
}
else if(left && up) {
alreadyCounted[i][j - 1] = true; // Show that this 'A' has already been counted
alreadyCounted[i - 1][j] = true; // Show that this 'A' has already been counted
currentLength += Math.max(findPathLengthRecursive(i, j - 1), findPathLengthRecursive(i - 1, j));
}
else if(left && down) {
alreadyCounted[i][j - 1] = true; // Show that this 'A' has already been counted
alreadyCounted[i + 1][j] = true; // Show that this 'A' has already been counted
currentLength += Math.max(findPathLengthRecursive(i, j - 1), findPathLengthRecursive(i + 1, j));
}
else if(right && up) {
alreadyCounted[i][j + 1] = true; // Show that this 'A' has already been counted
alreadyCounted[i - 1][j] = true; // Show that this 'A' has already been counted
currentLength += Math.max(findPathLengthRecursive(i, j + 1), findPathLengthRecursive(i - 1, j));
}
else if(right && down) {
alreadyCounted[i][j + 1] = true; // Show that this 'A' has already been counted
alreadyCounted[i + 1][j] = true; // Show that this 'A' has already been counted
currentLength += Math.max(findPathLengthRecursive(i, j + 1), findPathLengthRecursive(i + 1, j));
}
else if(left) {
currentLength++;
alreadyCounted[i][j - 1] = true; // Show that this 'A' has already been counted
findPathLengthRecursive(i, j - 1);
}
else if(up) {
currentLength++;
alreadyCounted[i - 1][j] = true; // Show that this 'A' has already been counted
findPathLengthRecursive(i - 1, j);
}
else if(right) {
currentLength++;
alreadyCounted[i][j + 1] = true; // Show that this 'A' has already been counted
findPathLengthRecursive(i, j + 1);
}
else if(down) {
currentLength++;
alreadyCounted[i + 1][j] = true; // Show that this 'A' has already been counted
findPathLengthRecursive(i + 1, j);
}
}
return currentLength;
}
无论我尝试什么,似乎只是返回的随机数与我要查找的23都不接近。
这是从第一个方法调用时递归方法的输出。
136 70 1个 3 70 58 1个 56 70 36 37 1个 3 60 53 69 85 66 69 85 66 54 43 63 51 49 79 84 109 142 2 1个 139 2 1个 87 116 119 118 132 3 4 3 100 5 4 2 1个 166 2 1个 1个 166
任何帮助都会非常有帮助,谢谢!
答案 0 :(得分:0)
char [][]mat;
boolean visit[][];
int rowSize , columnSize;
int dx[] = {-1 , 0 , 0 , +1};
int dy[] = { 0 , +1 , -1 , 0};
int rec(int row , int col){
visit[row][col] = true;
int ret = 0;
for(int k = 0 ; k < 4 ; ++k){
int nr = row+dx[k];
int nc = col+dy[k];
if(nr < 0 || nr >= rowSize || nc < 0 || nc >= columnSize || visit[nr][nc] && mat[nr][nc] != 'A'){
continue;
}
ret += 1 + rec(nr , nc);
}
return ret;
}
void main(){
//todo input the matris and rowSize , columnSize
//todo make all item of visit by 0;
int mx = 0;
for(int i = 0 ; i < rowSize; ++i){
for(int j = 0 ; j < columnSize; ++j){
int cur = rec(i ,j);
mx = mx > cur ? mx : cur;
}
}
//mx is answer
}
答案 1 :(得分:0)
已经有一个解决方案,但是我认为它不能正确重置访问状态,这可能使其错过重要的路径选项(同时,以前的总和最大问题显然已得到解决)。
如果您想学习一些东西并进行改进和完善,我建议将所有逻辑移至递归函数的开头:
如果任何条件为假,则只需返回0即可退出。
这使您可以仅在检查后将位置标记为已计数,然后针对所有方向递归调用该方法,而无需在那里进行大量检查并返回最大值+1。您可以调用无效位置,因为在递归函数中对此进行了检查。不要忘记使用递归调用的结果。
不重复检查将避免复制粘贴错误和额外的循环或方向数组的需要。
在退出递归函数时不要忘记取消标记。
编辑:伪代码可以更好地说明简化过程(您需要用相应的代码替换注释和“ ...”):
[('text', 'NN', 'I want to analyze this text')]
基本上