陷入困境

时间:2010-04-16 13:39:26

标签: c#

while (true)
{
    //read in the file
    StreamReader convert = new StreamReader("../../convert.txt");

    //define variables
    string line = convert.ReadLine();
    double conversion;
    int numberIn;
    double conversionFactor;

    //ask for the conversion information
    Console.WriteLine("Enter the conversion in the form (Amount, Convert from, Convert to)");
    String inputMeasurement = Console.ReadLine();
    string[] inputMeasurementArray = inputMeasurement.Split(',');


    //loop through the lines looking for a match
    while (line != null)
    {
        string[] fileMeasurementArray = line.Split(',');
        if (fileMeasurementArray[0] == inputMeasurementArray[1])
        {
            if (fileMeasurementArray[1] == inputMeasurementArray[2])
            {
                Console.WriteLine("The conversion factor for {0} to {1} is {2}", inputMeasurementArray[1], inputMeasurementArray[2], fileMeasurementArray[2]);

                //convert to int
                numberIn = Convert.ToInt32(inputMeasurementArray[0]);
                conversionFactor = Convert.ToDouble(fileMeasurementArray[2]);

                conversion = (numberIn * conversionFactor);
                Console.WriteLine("{0} {1} is {2} {3} \n", inputMeasurementArray[0], inputMeasurementArray[1], conversion, inputMeasurementArray[2]);
                break;
            }
        }
        else
        {
            Console.WriteLine("Please enter two valid conversion types \n");
            break;
        }
        line = convert.ReadLine();
    }
}

该文件包含以下内容:

ounce,gram,28.0
pound,ounce,16.0
pound,kilogram,0.454
pint,litre,0.568
inch,centimetre,2.5
mile,inch,63360.0

用户将输入类似6盎司,克

的内容

这个想法是通过检查文件中的第一个和第二个单词是否与用户输入的第二个和第三个单词相同来找到正确的行。

问题是,如果它检查第一行并且它使if语句失败,那么如果进入else语句并停止。我试图找到一种方法,它会在它找到正确的行之后停止但不是直到。如果有人输入的值不在文件中,那么它应该显示错误。

5 个答案:

答案 0 :(得分:5)

删除else子句中的break语句。这导致它退出循环。

您可以通过将转换因子读入内部数据结构来改进此代码,也许是由“from”转换单元键入的字典,其值为可能的输出单位及其转换因子的字典 - 或者是自定义键/值对,如果您只有一个可能的输出单位。这会将您的内部循环变为两阶段查找(更快),并且每次都必须重新读取转换文件。正如@Ben指出的那样,错误信息也在错误的位置。它需要在循环/查找之外,并且只有在找不到匹配项时才会执行。

示例代码 - 请注意此代码中没有输入验证:

var conversions = new Dictionary<string,Dictionary<string,double>>();
var convert = new StreamReader("../../convert.txt");
while ((var line = convert.ReadLine()) != null)
{
    string components = line.Split(',');
    Dictionary<string,double> unitConversions;
    if (conversions.ContainsKey( components[0] ))
    {
        unitConversions = conversions[components[0]];
    }
    else
    {
        unitConversions = new Dictionary<string,double>();
        conversions.Add( components[0], unitConversions );
    }
    unitConversions.Add( components[1], Convert.ToDouble( components[2] ) );
}

while (true)
{
    //ask for the conversion information     
    Console.WriteLine("Enter the conversion in the form (Amount, Convert from, Convert to)");     
    var inputMeasurement = Console.ReadLine();     
    var inputMeasurementArray = inputMeasurement.Split(',');

    bool converted = false;
    Dictionary<string,double> unitConversion;
    if (conversions.TryGetValue(  inputMeasurementArray[1], out unitConversion ))
    {
         double conversionFactor;
         if (unitConversion.TryGetValue( inputMeasurementArray[2], out conversionFactor ))
         {
             converted = true;
             conversion = Convert.ToDouble( inputMeasurementArray[0] ) * conversionFactor;
             Console.WriteLine("{0} {1} is {2} {3} \n", inputMeasurementArray[0], inputMeasurementArray[1], conversion, inputMeasurementArray[2]);              
         }
    }

    if (!converted)
    {
         Console.WriteLine("Please enter two valid conversion types\n");
    }
}

答案 1 :(得分:2)

我猜你明白你的代码在做什么,所以我不必指出break导致它停止。你只是想要做什么来完成你想要的。 break区块内的if是正确的,并会在找到匹配项后停止。

继续也不起作用,现在说如果第一行不匹配则会出错。

为什么你有外while循环?特别是,为什么要在循环中读取文件?读一遍,然后循环。

我认为您想要的是在行读取循环之上设置bool found = false;之类的内容。然后在成功的if块内,在found = true;之前设置break。完全摆脱else块,因为这不是错误。这只是意味着你还没有找到它。然后在循环之外,放

if (!found) Console.WriteLine("Please enter two valid conversion types \n");

使用found确定是否继续,循环整个文件后

答案 2 :(得分:1)

其他应该完全删除。

引入布尔“成功”标志,初始化为false并在找到值时将其设置为true

然后,在外面 while循环,

if (success == false) { 
    Console.WriteLine("Please enter two valid conversion types \n");
}

答案 3 :(得分:1)

要解决此问题,我会将算法的一部分提取到单独的方法中,以便您可以隔离流控制。我首先编写一个方法,在文件中搜索与用户输入匹配的转换设置:

private string[] FindConversionSetting(string[] input, StreamReader reader) 
{        
    do 
    {
        string line = reader.ReadLine();
        if (line != null) 
        {
            string[] settings = line.Split(',');
            bool sourcesMatch = string.Compare(input[1], settings[0], true) == 0;
            bool targetsMatch = string.Compare(input[2], settings[1], true) == 0;

            if (sourcesMatch && targetsMatch) 
            {                    
                return settings; // Match found
            }
        }
    } while (line != null);

    return null; // No match
}

接下来,创建一个名为ConvertAndDisplayInput的方法,以便在找到匹配项后隔离您要执行的代码 - 这就像上面的成功条件一样,所以我不会在此重复。

最后,我会编写控制逻辑(在这里显示单个转换,你可能希望调用者循环遍历这个,直到用户点击回车或其他东西):

// In Program.Main (for example)

Console.WriteLine("Enter the conversion in the form (Amount, Convert from, Convert to)");

string input = Console.ReadLine();

using (StreamReader reader = new StreamReader("../../convert.txt") 
{
    string[] conversionSetting = this.FindConversionSetting(input, reader);

    if (conversionSetting != null) 
    {
        this.ConvertAndDisplayInput(input, conversionSetting );
    }
    else 
    {
        Console.WriteLine("Please enter two valid conversion types \n");
    }
}

答案 4 :(得分:0)

如果tvanfosson回答不起作用。你可以用继续替换他提到的休息。它将使执行转到下一个循环