我有一个由文本列表组成的文件,如下所示:
ABC Abbey something
ABD Aasdasd
第一个字符串将始终是3的长度。所以我想循环遍历文件内容,将前3个字母存储为Key并保留为值。我正在删除它们之间的空格和Substringing如下存储。键工作正常,但我存储值的行返回错误。的 ArgumentOutOfRangeException
这是导致问题的确切代码。
line.Substring(4, line.Length)
如果我在0和line.length之间调用subString,它可以正常工作。只要我在1和向上之间调用它 - line.length我就会得到错误。老实说,没有得到它,并坚持了几个小时。请一些帮助。
class Program {
static string line;
static Dictionary<string, string> stations = new Dictionary<string, string>();
static void Main(string[] args) {
var lines = File.ReadLines("C:\\Users\\username\\Desktop\\a.txt");
foreach (var l in lines) {
line = l.Replace("\t", "");
stations.Add(line.Substring(0, 3), line.Substring(4, line.Length));//error caused by this line
}
foreach(KeyValuePair<string, string> item in stations) {
//Console.WriteLine(item.Key);
Console.WriteLine(item.Value);
}
Console.ReadLine();
}
}
答案 0 :(得分:3)
这是因为文档指定它将抛出ArgumentOutOfRangeException if:
startIndex
加length
表示不在此实例中的位置。
签名:
public string Substring(int startIndex, int length)
由于您使用的是line.Length
,因此您知道startIndex
加length
将是4+line.Length
,这绝对不是此实例的位置。
我建议使用one parameter version:
public string Substring(int startIndex)
因此line.Substring(3)
(spotting that的@ adv12奖励)。从这里开始,您应该只提供startIndex
。当然你可以使用line.SubString(3,line.Length-3)
,但是一如既往地更好地使用库,因为库是为了使程序变得傻瓜(这不是冒犯性的,只是确保你减少这个任务的大脑周期量) )。但是请注意,如果出现错误,它仍会引发错误:
startIndex
小于零或大于此实例的长度。
更好地提供3
小于或等于line.length
...
也许你应该看一下正则表达式捕获。现在,文件中的每个键都包含三个字符。但是有可能在(接近)未来四个角色是可能的。使用正则表达式捕获,您可以指定一种模式,以便在解析过程中发生错误的可能性较小。
答案 1 :(得分:2)
你需要实际得到的总长度小于:
line.Substring(4, line.Length - 4) //subtract the chars which you're skipping
你的字符串:
ABC Abbey something
Length = 19
Start = 4
Remaining chars = 19 - 4 = 15 //and you are expecting 19, that is the error
答案 2 :(得分:1)
我知道这是一个迟到的答案,没有解决你的代码有什么问题,但我觉得其他人已经做过了。相反,我有不同的方法来使字典完全不涉及子字符串,所以它更健壮,恕我直言。
只要您可以保证两个值始终由制表符分隔,那么即使键中有更多或更少的字符,这也会起作用。它使用LINQ,从.NET 3.5开始应该没问题。
// LINQ
using System.Linq;
// Creates a string[][] array with the list of keys in the first array position
// and the values in the second
var lines = File.ReadAllLines(@"path/to/file.txt")
.Select(s => s.Split('\t'))
.ToArray();
// Your dictionary
Dictionary<string, string> stations = new Dictionary<string, string>();
// Loop through the array and add the key/value pairs to the dictionary
for (int i = 0; i < lines.Length; i++)
{
// For example lines[i][0] = ABW, lines[i][1] = Abbey Wood
stations[lines[i][0]] = lines[i][1];
}
// Prove it works
foreach (KeyValuePair<string, string> entry in stations)
{
MessageBox.Show(entry.Key + " - " + entry.Value);
}
希望这是有道理的并给你一个考虑的替代方案; - )