Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/384.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 重构(C)伪代码以删除goto_Java_C_Goto - Fatal编程技术网

Java 重构(C)伪代码以删除goto

Java 重构(C)伪代码以删除goto,java,c,goto,Java,C,Goto,在Java中重构的最佳实践是什么 while (1) { // initialisation for (int i = 0; i < MAX_ATTEMPT; i++) { if (try_something()) goto step2; } continue; step2: for (int i = 0; i < MAX_ATTEMPT; i++) { if (try_next_thing()) goto step3; } con

在Java中重构的最佳实践是什么

while (1) {
  // initialisation

  for (int i = 0; i < MAX_ATTEMPT; i++) {
    if (try_something()) goto step2;
  }
  continue;

step2:  
  for (int i = 0; i < MAX_ATTEMPT; i++) {
    if (try_next_thing()) goto step3;
  }
  continue;

step3:
  ...
}    
while(1){
//初始化
对于(int i=0;i
您首先要确定代码试图实现的目标:

  • 反复执行以下操作:
  • 调用try_something(),最多可调用MAX_尝试次数,如果从未返回true,则重新启动
  • 调用try_next_thing(),最多可调用最大尝试次数,如果从未返回true,则重新启动
然后,编写这样做的代码,例如:

while (true) {

    int i;

    for (i = 0; i < MAX_ATTEMPT && !try_something(); ++ i)
        ;
    if (i == MAX_ATTEMPT)
        continue;

    for (i = 0; i < MAX_ATTEMPT && !try_next_thing(); ++ i)
        ;
    if (i == MAX_ATTEMPT)
        continue;

    // etc.

}
while(true){
int i;
对于(i=0;i
还有很多其他的表达方式。例如,您可以将每个步骤分解为一个方法,并利用这样一个事实,即当一个参数为false时,&&将停止计算它的参数:

boolean doFirstThing () {
    int i;
    for (i = 0; i < MAX_ATTEMPTS && !try_something(); ++ i)
        ;
    return i < MAX_ATTEMPTS;
}

boolean doSecondThing () {
    int i;
    for (i = 0; i < MAX_ATTEMPTS && !try_other_thing(); ++ i)
        ;
    return i < MAX_ATTEMPTS;
}

// then, elsewhere
while (true)
    doFirstThing() && doSecondThing();
boolean doFirstThing(){
int i;
对于(i=0;i

或者别的什么。我不确定我是否会称后者为“最佳实践”,因为它有点模糊(这并不是说它在某些情况下不合适),但它只是一个例子。一般来说,当移植到另一种语言时:分析原文->它应该做什么?->在目标语言中重新实现。优先考虑的是代码的正确性,其次(但不远落后于)是清晰性。

对于字面意思,但不是你能做的最好的翻译。使用break作为goto不是一个好主意,除非您必须生成代码,并且没有简单的方法可以解决这个问题

while (true) {
    // initialisation

    step2:
    {
        for (int i = 0; i < MAX_ATTEMPT; i++) {
            if (try_something()) break step2;
        }
        continue;
    }

    step3:
    {
        for (int i = 0; i < MAX_ATTEMPT; i++) {
            if (try_next_thing()) break step3;
        }
        continue;
    }

    step4:
    ...
}
while(true){
//初始化
步骤2:
{
对于(int i=0;i
也许不是最好的解决方案,但我通常会:

boolean success = false;

for (int i = 0; i < MAX_ATTEMPT && !success; i++) {
    success = try_something()
}

if (success) {
    success = false;
    for (int i = 0; i < MAX_ATTEMPT && !success; i++) {
        success = try_next_thing();
    }
}
boolean success=false;
for(int i=0;i

希望这会有所帮助。

我会首先将C代码重构为不太重复的代码:

enum { STEP1, STEP2, STEP3, /*...*/ };

typedef int ThingToTry();

ThingToTry *things_to_try[MAX_STEP] = {
    try_something,
    try_next_thing,
    /*...*/
};

int next_step (int (*thing_to_try)(), int true_step, int false_step) {
    for (int i = 0; i < MAX_ATTEMPT; i++) {
        if (thing_to_try()) return true_step;
    }
    return false_step;
}

/*...*/

    step = STEP1;
    while (step != MAX_STEP) {
        if (step == STEP1) {
            /*...initialization */
        }
        step = next_step(things_to_try[step], step+1, STEP1);
    }
enum{STEP1,STEP2,STEP3,/*…*/};
typedef int ThingToTry();
ThingToTry*要尝试的事情[MAX\u STEP]={
试试看,
试试下一件事,
/*...*/
};
int下一步(int(*要尝试的东西)(),int真步,int假步){
对于(int i=0;i
Java中的相应代码:

enum StepEnum { STEP1, STEP2, STEP3, //...
              }

interface ThingToTry {
   bool do_it ();
}

class TrySomething extends ThingToTry //...
class TryNextThing extends ThingToTry //...

StepEnum next_step (ThingToTry thing_to_try,
                    StepEnum true_step, StepEnum false_step) {
    for (int i = 0; i < MAX_ATTEMPTS; ++i) {
        if (thing_to_try.do_it()) return true_step;
    }
    return false_step;
}

//...
    ThingToTry[MAX_STEP] things_to_try = {
        new TrySomething,
        new TryNextThing,
        //...
    };

    while (step != MAX_STEP) {
        if (step == STEP1) {
            //...initialization
        }
        StepEnum true_step = StepEnum.values()[step.ordinal()+1];
        step = next_step(things_to_try[step.ordinal()], true_step, STEP1);
    }
枚举步骤枚举{STEP1,STEP2,STEP3,//。。。
}
接口组件{
bool do_it();
}
类TrySomething扩展了ThingToTry/。。。
类TryNextThing扩展ThingToTry/。。。
步骤列举下一步(要尝试的事情),
步骤枚举真步骤,步骤枚举假步骤){
对于(int i=0;i
我很想封装这些步骤,并使用类似于状态机的东西:

enum Step {
    STEP1 {
        @Override
        public Step attempt() {
            for (int i = 0; i < MAX_ATTEMPT; i++) {
                if (try_something()) return STEP2; // advance to next step
            }
            return STEP1; // return to step 1
        }
    },
    STEP2 {
        @Override
        public Step attempt() {
            for (int i = 0; i < MAX_ATTEMPT; i++) {
                if (try_next_thing()) return STEP3; // advance to next step
            }
            return STEP1; // return to step 1
        }
    },
    STEP3 { /* etc. */ },
    . . .
    ;
    public abstract Step attempt();
}
typedef bool (state_t*)(void);

state_t state [STATES_N] = {   // array of function pointers
  &try_something,
  &try_next_thing,
  ...
};


int state = 0;  

while (1) {

  for (int i = 0; i < MAX_ATTEMPT; i++) {

    if(try[state]()) {
      state++;
      if(state == STATES_N) {
        state = 0;
      }
    }
  }
}

对我来说,最有效的方法是在函数之间拆分逻辑,我的想法如下:

bool attempt_something() {
   for(int i = 0; i < MAX_ATTEMPT: i++) {
      if (try_something())
         return true;
   }
   return false;
}

bool attempt_something_else() {
   for(int i = 0; i < MAX_ATTEMPT: i++) {
      if (try_something_else())
         return true;
   }
   return false;
}

首先将代码转换为C语言中的面向对象设计。您的代码本质上是一个状态机,因此您应该能够用状态机替换它

典型的基于函数指针的状态机示例:

enum Step {
    STEP1 {
        @Override
        public Step attempt() {
            for (int i = 0; i < MAX_ATTEMPT; i++) {
                if (try_something()) return STEP2; // advance to next step
            }
            return STEP1; // return to step 1
        }
    },
    STEP2 {
        @Override
        public Step attempt() {
            for (int i = 0; i < MAX_ATTEMPT; i++) {
                if (try_next_thing()) return STEP3; // advance to next step
            }
            return STEP1; // return to step 1
        }
    },
    STEP3 { /* etc. */ },
    . . .
    ;
    public abstract Step attempt();
}
typedef bool (state_t*)(void);

state_t state [STATES_N] = {   // array of function pointers
  &try_something,
  &try_next_thing,
  ...
};


int state = 0;  

while (1) {

  for (int i = 0; i < MAX_ATTEMPT; i++) {

    if(try[state]()) {
      state++;
      if(state == STATES_N) {
        state = 0;
      }
    }
  }
}
typedef bool(state_t*)(void);
state\u t state[STATES\u N]={//函数指针数组
&试试看,
&试试下一件事,
...
};
int state=0;
而(1){
对于(int i=0;i

要将其转换为Java OO,我想您可以将每个状态交换为一个类的对象,其中该类有一个try函数。

至于抑制gotos,其他提供了答案。至于java部分:您的期望是什么?你在寻找面向对象的重构吗?不,只是简单的流控制。为什么要重构这段代码?代码可读且易于理解。你为什么不删除
goto
语句?@Bart-Java没有goto。[:blush:]我误解了你的问题。我以为你想用C进行重构。你会想在第一次发现成功后停止循环。@Lundin这就是为什么循环条件会添加
&&!成功
addon。对不起,下次我会仔细看:)这很可爱,但OP要求重构成Java,而这不是Java。@TedHopp:我是先重构C代码的。谢谢,我已经做了你的第一个解决方案,但我不喜欢I的范围。看