0

我正在尝试使用 c# 读取 .txt 文件并显示其内容,但我收到错误IndexOutOfRangeException,错误代码为.txt 0xc000013a

这是我的代码:

static void Main(string[] args)
    {
        StreamReader sStreamReader = new StreamReader("d:\\TEST.txt");
        while (!sStreamReader.EndOfStream)
        {
            string sLine = "";
            if (sLine != null)
            {
                sLine = sStreamReader.ReadLine();
                if (sLine != null)
                {
                    string[] rows = sLine.Split(",".ToCharArray());
                    double a = Convert.ToDouble(rows[1]);
                    Console.Write(a);
                    int b = Convert.ToInt32(rows[3]);
                    Console.WriteLine(b);
                    Console.WriteLine();
                }
            }
        }
    }

我的文本文件如下:

1,2,3,4,5,6,7

1,2,3,4,5,6,7

5,6,2,7,3,8,4

3,4,3,4,3

5,3,23,12

12,30000,12,99
4

4 回答 4

2

我会将其更改为以下内容:

static void Main(string[] args)
    {
        // StreamReader is IDisposable which should be wrapped in a using statement
        using (StreamReader reader = new StreamReader(@"d:\TEST.txt")) 
        {
            while (!reader.EndOfStream)
            {
                string line = reader.ReadLine();
                // make sure we have something to work with
                if (String.IsNullOrEmpty(line)) continue;

                string[] cols = line.Split(',');
                // make sure we have the minimum number of columns to process
                if (cols.Length < 4) continue;

                double a = Convert.ToDouble(cols[1]);
                Console.Write(a);
                int b = Convert.ToInt32(cols[3]);
                Console.WriteLine(b);
                Console.WriteLine();
            }
        }
    }

这里有一些注意事项:

  1. StreamReader 实现 IDisposable,因此您应该将它包装在 using 子句中,以便正确处理它。
  2. 不要命名诸如“sLine”之类的东西。这种形式的匈牙利语通常被认为是非常糟糕的做法。甚至微软也说不要这样做。
  3. 您正在处理列,而不是行。所以应该适当地命名该变量。
  4. 在盲目访问它们之前,请始终进行测试以确保您拥有所需的所有列。
  5. 通常,我不会使用 Convert.ToDouble 或 Convert.ToInt32。使用 TryParse 确保它能够转换要安全得多。如果 cols[1] 和 cols[3] 有非数字数据,您的代码将会崩溃。
  6. 您可以在字符串前面使用@ 符号来告诉编译器它不需要转义。
  7. 简单地“继续”循环而不是将其包装在 if 语句中要干净得多。
  8. 将 String 变量设置为空白字符串,然后立即将其设置为其他值会导致空白在整个范围内保留在内存中。换句话说,它在浪费内存。诚然,在这种情况下,它是一种微优化,但始终使用最佳实践并没有什么坏处。
于 2012-08-03T06:11:26.567 回答
1

这是您可以更简单的方法:

        string[] lines = File.ReadAllLines("d:\\TEST.txt");
        foreach (var line in lines.Where(line => line.Length > 0))
        {
            string[] numbers = line.Split(',');

            // It checks whether numbers.Length is greater than 
            // 3 because if maximum index used is 3 (numbers[3]) 
            // than the array has to contain at least 4 elements
            if (numbers.Length > 3)
            {
                double a = Convert.ToDouble(numbers[1]);
                Console.Write(a);
                int b = Convert.ToInt32(numbers[3]);
                Console.Write(b);
                Console.WriteLine();
            }
        }
于 2012-08-03T06:14:58.180 回答
1

row.Length您是否考虑过在访问之前检查row[1]row[3]

我怀疑你的空行是问题

于 2012-08-03T06:00:32.393 回答
0

您应该考虑使用:

if (!string.IsNullOrEmpty(sLine))

代替

if (sLine != null)

你有这个例外,因为有些行是空的。

但是,在使用 StreamReader 时,您应该使用以下方式编写代码:

using(var reader = new StreamReader(@"d:\\TEST.txt"))
{
    string line;
    while ((line= reader.ReadLine()) != null)
    {
        if (string.IsNullOrEmpty(line)) continue;

        var rows = line.Split(",".ToCharArray());
        var a = Convert.ToDouble(rows[1]);
        Console.Write(a);
        var b = Convert.ToInt32(rows[3]);
        Console.WriteLine(b);
        Console.WriteLine();
    }
}

问候,

凯文

于 2012-08-03T06:08:40.297 回答