0

我有以下代码;目的是返回数组中按字母顺序排列的最小成员。

public String smallest() {
String smallest = "";
int i = 0;
while(log[i] != null) {
    int nextIndex = i+1;
    if(log[nextIndex] == null) {
        break;
    }
    if(log[i].compareToIgnoreCase(log[nextIndex]) >0) {
        smallest = log[nextIndex];
    }
    else {
        smallest = log[i];
    }
    i++;
}
if(log[i].compareToIgnoreCase(smallest) <0) {
    smallest = log[i];
}
return smallest;
}

当我运行测试仪时,其中两个测试失败,另外两个继续正常。第一个是成功测试的示例,后者是失败测试之一的示例。

public void test_3Elements_smallest_in_middle() {
    strLog.insert("string 2"); strLog.insert("string 1");
    strLog.insert("string 3"); 

    assertEquals(strLog.smallest(), "string 1");
}

public void test_3Elements_smallest_at_beginning() {
    strLog.insert("string 1"); strLog.insert("string 2");
    strLog.insert("string 3"); 

    assertEquals(strLog.smallest(), "string 1");
}

我到底能做些什么来解决这个问题?更具体地说,对于后一个失败的那个,它给了我一个错误,关于它期待字符串 [2] 但它是字符串 [1]。这让我感到困惑;如果它可以在数组中间挑选出最小的,为什么它不能在开头挑选出最小的?

4

3 回答 3

2

当这个单行解决方案可以完成这项工作时,看起来你让事情变得过于复杂:

return Collections.min(Arrays.asList(log), String.CASE_INSENSITIVE_ORDER);
于 2013-09-18T23:34:37.393 回答
1

假设 java 这样的东西应该可以工作。我没有测试它。C# 有类似的语法。可以用索引来完成,但这更干净。

public String smallest() {
    String smallest = log[0]; //assumes atleast one element in list

    for (String message : log){
       if ( message != null && message.compareToIgnoreCase(smallest) < 0 ){
         smallest = message;
       }
    }

    return message;

    }

此时在您的代码中:

if(log[i].compareToIgnoreCase(log[nextIndex]) >0) {
    smallest = log[nextIndex];
}

您只比较列表中的两个连续项目,而不是列表中的所有项目。这就是为什么你的答案是错误的。如果列表已排序,这将起作用,但是首先取出最小的项目会很简单。

于 2013-09-18T22:34:54.940 回答
0

显然,您的算法定义不明确。您正在将项目与他们的下一个进行比较。试试这个:

String minText = log[0];

for (int i = 1; i < log.length; i++)
{
    if (minText.compareToIgnoreCase(log[i]) > 0)
    {
        minText = log[i];
    }
}

Louis Wasserman 也是正确的,但我想向您展示算法。基本上,我们最初将 minText 设置为日志中的第一个元素。然后,从第二个元素到最后一个元素,我们一直在查看当前元素是否小于当前存储的 minText。如果是这样,我们将该值分配给 minText。

于 2013-09-18T23:43:03.400 回答