Java 试图让游戏工作,循环条件
我会尽量简单清楚地解释我得到了什么和我需要什么 我有一个二维数组,由char元素组成。我必须从底部拍一张照片,用“·”表示。快照从底部(a.length-1)到顶部(0),根据快照方向在墙上进行反弹Java 试图让游戏工作,循环条件,java,arrays,loops,for-loop,break,Java,Arrays,Loops,For Loop,Break,我会尽量简单清楚地解释我得到了什么和我需要什么 我有一个二维数组,由char元素组成。我必须从底部拍一张照片,用“·”表示。快照从底部(a.length-1)到顶部(0),根据快照方向在墙上进行反弹 if (dirDisp == 3){ for(int x = 3, y = 0; x < 5 & y < 2; x++, y++) { if(a[(a.length-1) - y][(a[x].length-1) / 2 +
if (dirDisp == 3){
for(int x = 3, y = 0; x < 5 & y < 2; x++, y++) {
if(a[(a.length-1) - y][(a[x].length-1) / 2 + x] == EMPTY)
a[(a.length-1) - y][(a[x].length-1) / 2 + x] = '·';
}
for(int x = 0, y = 1; x < 9 & y < 11; x++, y++) {
if(a[(a.length-1) - y][(a[x].length-1) - x] == EMPTY)
a[(a.length-1) - y][(a[x].length-1) - x] = '·';
}
for(int x = 0, y = 9; x < 5 & y < 14; x++, y++) {
if(a[(a.length-1) - y][x] == EMPTY)
a[(a.length-1) - y][x] = '·';
}
}
放炮必须在到达第一个要清空的字符时停止。我试着使用“中断”和“继续”。还有firstLoop:{}的使用。我还尝试在循环的每个部分使用布尔值,但我还没有让它起作用。我需要一点帮助
如果有什么不清楚的,就问吧
PD:该快照有3个“for”循环,第一个循环用于填充从底部到第一面墙的阵列,第二个循环用于填充墙和墙之间的空间,第三个循环用于填充从对面到顶部的墙。
PD2:“r”线在那里,你可以看到实际发生了什么
使用布尔值后:
a b a b y a r y y
y a o y g r o g g
g o y o a y y a y
y o a a g o o b a
o o r a o r g y y
r r r r r r r r r
·
·
主类 } 尝试一种新的拍摄方式 在你回答了所有的问题之后,我用了一种新的方法来射击,比第一种方法简单得多,使用了while循环和更多的常量名称,使它更容易理解 职位类别仍然是相同的 我将把代码放在这里,带有正向射击方向:
public static void getTrayectory (char [][] a,int shootDirection){
int x = 0, y = 0;
START = ((RIGHT_WALL)/2) + shootDirection;
a [BOTTOM][START] = SHOT;
if(shootDirection > 0){
while (!isOut(BOTTOM-x,START+y) && emptyCell(BOTTOM-x,START+y)){
b [BOTTOM - x][START + y] = SHOT;
x++; y++;
}
y = 0; x=x-1;
while (!isOut(BOTTOM-x,RIGHT_WALL-y) && emptyCell(BOTTOM-x,RIGHT_WALL-y)){
b [BOTTOM-x][RIGHT_WALL-y] = SHOT;
x++; y++;
}
y = 0; x=x-1;
while (!isOut(BOTTOM-x,LEFT_WALL+y) && emptyCell(BOTTOM-x,LEFT_WALL+y)){
b [BOTTOM-x][LEFT_WALL+y] = SHOT;
x++; y++;
}
y = 0;
while (!isOut(BOTTOM-x,RIGHT_WALL-y) && emptyCell(BOTTOM-x,RIGHT_WALL-y)){
b [BOTTOM-x][RIGHT_WALL-y] = SHOT;
x++; y++;
}
}
}
您还需要使用它来编译它;)
publicstaticchar[]b=新字符[25][9];
公共静态字符为空='-';
公共静态字符快照='x';
公共静态扫描仪sc=新扫描仪(System.in);
公共静态方向;
公共静态int-BOTTOM=b.length-1;
公共静态int RIGHT_WALL=b[0]。长度-1;
公共静态int左墙=0;
公共静态int TOP=0;
公共静态int中心=((右墙)/2);
公共静态int开始=((右墙)/2)+方向;
公共静态空白填充(字符[][]b){
对于(int x=0;x右墙)返回true;
如果(y
问题是,它是有效的,但是,在emptyCell方法中有一个错误。它返回b[x-1][y]==空,因为如果我使用return b[x][y],它会得到一个边界外错误。由于x-1,循环在应该停止之前停止一行,我不知道如何修改它以使其正常工作
另一件事是,我想做一个更简单的方法,但即使有下面的小例子,我也不知道如何使用我的常量。我希望你能帮我做,一定很简单,但我不知道:用isOut方法和emptyCell方法,答案一定很接近。谢谢你,也很抱歉这么长的线程。据我所知,最接近你的解决方案是在
空白检查处放置一个else
,然后告诉它从可能中断的第一个循环开始中断。然后,设置一个告诉它停止的变量,然后使剩余的for
循环对该变量有条件,这样它就不会从那里拾取
因此,它可能是这样的(但请记住,以下是一个很糟糕的解决方法,代码的整体结构应该在之后立即改进):
请记住,调试此代码时遇到问题的原因是,正如其他人所建议的,代码非常模糊。无论一个人有多丰富的经验,这都是一件很难调试的事情
这就是为什么每个人都建议我们应该编写干净的代码。记住,每个人都会犯错。一旦您了解了如何用一种语言编写程序(显然,您自己也知道),最大的区别在于您自己对代码的理解程度,这样您就可以更容易地看到错误。永远不要以为你自己写了一段代码就理解了它。制作大量变量,给它们有意义的名称,将程序分成若干部分,制作大量与程序必须处理的实体相对应的类型,也给它们有意义的名称,定位重复的代码模式,将它们转换为函数/方法(带或不带参数化部分),并给它们有意义的名称
即使你在那一点上找不到自己的错误,别人至少会更容易帮助你 如果中断条件复杂,我建议使用while循环。使用好的方法名也会使代码更具可读性
while (!outOfBounds(x,y) && emptyCell(x,y) {
a[x][y] = '.';
moveCursor(direction);
}
...
boolean emptyCell(int x, int y){
return a[x][y] == EMPTY;
}
boolean outOfBounds(int x, int y){
if (x<0) return true;
if (y<0) return true;
if (x>LIMIT_X) return true;
if (y>LIMIT_Y) return true;
return false;
}
void moveCursor(direction){
if (direction==DOWN_RIGHT){
x++;
y++;
if (x > X_LIMIT){
x-=2;
direction = DOWN_LEFT;
}
...
}
while(!outOfBounds(x,y)和&emptyCell(x,y){
a[x][y]=';
移动光标(方向);
}
...
布尔空单元格(整数x,整数y){
返回一个[x][y]==空;
}
布尔出边界(整数x,整数y){
如果(xLIMIT__Y)返回true;
返回false;
}
无效移动光标(方向){
如果(方向==向下\向右){
x++;
y++;
如果(x>x_极限){
x-=2;
方向=向下/向左;
}
...
}
我刚刚编写了这个很小的方法,它正在执行您想要的操作。但是它被一个rnd char数组填充。请参阅我的中断条件
private void shot() {
char charArray[][] = new char[100][20];
Random r = new Random();
for(int i = 0;i<charArray.length;++i) {
for(int j = 0;j<charArray[0].length;++j) {
if(r.nextInt(5) == 0) {
charArray[i][j] = (char) (r.nextInt(26)+65);
}
}
}
boolean shotRight = false;
for(int i = charArray.length-1,j = charArray[0].length-1;i>0;--i) {
System.out.println(i + " " + j);
// break condition
if(charArray[i][j] != '\u0000') break;
if(shotRight) {
charArray[i][j] = '.';
++j;
}
else {
charArray[i][j] = '.';
--j;
}
if(j <= 0) {
shotRight = true;
}
if(j >= charArray[0].length-1) {
shotRight = false;
}
}
for(int i = 0;i<charArray.length;++i) {
for(int j = 0;j<charArray[0].length;++j) {
System.out.print(((charArray[i][j] == '\u0000') ? " ":charArray[i][j] + " ") + " ");
}
System.out.println();
}
}
private void shot(){
字符数组[][]=新字符[100][20];
随机r=新随机();
对于(int i=0;i您似乎使用了位AND运算符&
,当您应该使用逻辑AND时&&
。在这种情况下,我认为它们的工作原理是一样的,但您仍然应该更正它们。我已经尝试了此代码,它正是我所做的,但它不起作用:它只显示以前的快照
public static void getTrayectory (char [][] a,int shootDirection){
int x = 0, y = 0;
START = ((RIGHT_WALL)/2) + shootDirection;
a [BOTTOM][START] = SHOT;
if(shootDirection > 0){
while (!isOut(BOTTOM-x,START+y) && emptyCell(BOTTOM-x,START+y)){
b [BOTTOM - x][START + y] = SHOT;
x++; y++;
}
y = 0; x=x-1;
while (!isOut(BOTTOM-x,RIGHT_WALL-y) && emptyCell(BOTTOM-x,RIGHT_WALL-y)){
b [BOTTOM-x][RIGHT_WALL-y] = SHOT;
x++; y++;
}
y = 0; x=x-1;
while (!isOut(BOTTOM-x,LEFT_WALL+y) && emptyCell(BOTTOM-x,LEFT_WALL+y)){
b [BOTTOM-x][LEFT_WALL+y] = SHOT;
x++; y++;
}
y = 0;
while (!isOut(BOTTOM-x,RIGHT_WALL-y) && emptyCell(BOTTOM-x,RIGHT_WALL-y)){
b [BOTTOM-x][RIGHT_WALL-y] = SHOT;
x++; y++;
}
}
}
public static char [][] b = new char [25][9];
public static char EMPTY = '-';
public static char SHOT = 'x';
public static Scanner sc = new Scanner(System.in);
public static int shootDirection;
public static int BOTTOM = b.length - 1;
public static int RIGHT_WALL = b[0].length - 1;
public static int LEFT_WALL = 0;
public static int TOP = 0;
public static int CENTER = ((RIGHT_WALL)/2);
public static int START = ((RIGHT_WALL)/2) + shootDirection;
public static void fill (char [][] b){
for (int x = 0; x < b.length; x++){
for (int y = 0; y < b[x].length;y++){
b [x][y] = EMPTY;
b [10][y] = 'A';
}
}
}
public static void show (char [][] b){
for (int x = 0; x < b.length; x++){
System.out.println();
for (int y = 0; y < b[x].length; y++){
System.out.print(" "+b [x][y]+" ");
}
}
}
public static boolean isOut (int x,int y){
if(x < TOP)return true;
if(y > RIGHT_WALL)return true;
if(y < LEFT_WALL)return true;
return false;
}
static boolean emptyCell(int x, int y){
return b [x-1][y] == EMPTY;
}
if (dirDisp == 3){
boolean foundObstacle = false;
for(int x = 3, y = 0; x < 5 & y < 2; x++, y++){
if(a[(a.length-1) - y][(a[x].length-1) / 2 + x] == EMPTY)
a[(a.length-1) - y][(a[x].length-1) / 2 + x] = '·';
else {
foundObstacle = true;
break;
}
}
if(!foundObstacle) {
for(int x = 0, y = 1; x < 9 & y < 11; x++, y++){
if(a[(a.length-1) - y][(a[x].length-1) - x] == EMPTY)
a[(a.length-1) - y][(a[x].length-1) - x] = '·';
else {
foundObstacle = true;
break;
}
}
}
if(!foundObstacle) {
for(int x = 0, y = 9; x < 5 & y < 14; x++, y++){
if(a[(a.length-1) - y][x] == EMPTY)
a[(a.length-1) - y][x] = '·';
else break;
}
}
}
if (dirDisp == 3){
boolean foundObstacle = false;
for(int x = 3, y = 0; x < 5 & y < 2 && !foundObstacle; x++, y++){
if(a[(a.length-1) - y][(a[x].length-1) / 2 + x] == EMPTY)
a[(a.length-1) - y][(a[x].length-1) / 2 + x] = '·';
else {
foundObstacle = true;
break;
}
}
if(!foundObstacle) {
// At its first iteration, this loop finds the '·' symbol placed by the previous one.
// So I've made it start from the second.
for(int x = 1, y = 2; x < 9 & y < 11 && !foundObstacle; x++, y++){
if(a[(a.length-1) - y][(a[x].length-1) - x] == EMPTY)
a[(a.length-1) - y][(a[x].length-1) - x] = '·';
else {
foundObstacle = true;
break;
}
}
}
if(!foundObstacle) {
for(int x = 0, y = 9; x < 5 & y < 14 && !foundObstacle; x++, y++){
if(a[(a.length-1) - y][x] == EMPTY)
a[(a.length-1) - y][x] = '·';
else break;
}
}
}
while (!outOfBounds(x,y) && emptyCell(x,y) {
a[x][y] = '.';
moveCursor(direction);
}
...
boolean emptyCell(int x, int y){
return a[x][y] == EMPTY;
}
boolean outOfBounds(int x, int y){
if (x<0) return true;
if (y<0) return true;
if (x>LIMIT_X) return true;
if (y>LIMIT_Y) return true;
return false;
}
void moveCursor(direction){
if (direction==DOWN_RIGHT){
x++;
y++;
if (x > X_LIMIT){
x-=2;
direction = DOWN_LEFT;
}
...
}
private void shot() {
char charArray[][] = new char[100][20];
Random r = new Random();
for(int i = 0;i<charArray.length;++i) {
for(int j = 0;j<charArray[0].length;++j) {
if(r.nextInt(5) == 0) {
charArray[i][j] = (char) (r.nextInt(26)+65);
}
}
}
boolean shotRight = false;
for(int i = charArray.length-1,j = charArray[0].length-1;i>0;--i) {
System.out.println(i + " " + j);
// break condition
if(charArray[i][j] != '\u0000') break;
if(shotRight) {
charArray[i][j] = '.';
++j;
}
else {
charArray[i][j] = '.';
--j;
}
if(j <= 0) {
shotRight = true;
}
if(j >= charArray[0].length-1) {
shotRight = false;
}
}
for(int i = 0;i<charArray.length;++i) {
for(int j = 0;j<charArray[0].length;++j) {
System.out.print(((charArray[i][j] == '\u0000') ? " ":charArray[i][j] + " ") + " ");
}
System.out.println();
}
}