У меня большой текстовый файл записей, каждая из которых разделена новой строкой. Каждой записи предшествует двухзначное число, которое указывает ее тип. Вот пример:
....
30AA ALUMINIUM ALLOY LMELMEUSD2.00 0.35 5101020100818
40AADFALUMINIUM ALLOY USD USD 100 1 0.20000 1.00 0 100 140003
50201008180.999993 0.00 0.00 120100818
60 0F 1 222329 1.000000 0 0 -4667 -4667 4667 4667
50201008190.999986 0.00 0.00 120100819
60 0F 1 222300 1.000000 0 0 -4667 -4667 4667 4667
40AADOALUMINIUM ALLOY USD USD 100 1 0.20000 1.00 0 100 140001
50201009150.000000 0.17 0.17 120100915
60 1200C 1 101779 0.999800 0 0 -4666 -4666 4665 4665
60 1200P 1 0 0.000000 0 0 0 0 0 0
60 1225C 1 99279 0.999800 -1 -1 -4667 -4667 4665 4665
60 1225P 1 0 0.000000 0 0 0 0 0 0
60 1250C 1 96780 0.999800 0 0 -4666 -4666 4665 4665
60 1250P 1 0 0.000000 0 0 0 0 0 0
60 1275C 1 94280 0.999800 -1 -1 -4667 -4667 4665 4665
60 1275P 1 0 0.000000 0 0 0 0 0 0
60 1300C 1 91781 0.999800 0 0 -4666 -4666 4665 4665
60 1300P 1 0 0.000000
.......
Файл содержит иерархические отношения, основанные на двухзначных префиксах. Вы можете думать о «30» строках, содержащих «40», как о детях; «40» строк, содержащих «50», и «50», содержащих «60». После анализа эти строки и связанные с ними префиксы будут, очевидно, отображаться в тип clr, отображение «30» на «ContractGroup», отображение «40» на «InstrumentTypeGroup», «50» на «ExpirationGroup» и т. Д.
Я пытаюсь использовать функциональный подход к синтаксическому анализу, а также сокращаю потребление памяти с помощью метода отложенной загрузки, поскольку этот файл очень большой. Мой первый шаг заключается в создании генератора для выдачи по одной строке за раз, что-то вроде этого:
public static IEnumerable<string> TextFileLineEnumerator()
{
using (StreamReader sr = new StreamReader("BigDataFile.txt"))
{
while (!sr.EndOfStream)
{
yield return sr.ReadLine();
}
}
}
Это позволяет мне использовать Linq против текстового файла и обрабатывать строки в виде потока.
Моя проблема заключается в попытке обработать этот поток в его композиционную структуру коллекции, вот первая попытка:
var contractgroups = from strings in TextFileLineEnumerator()
.SkipWhile(s => s.Substring(0, 2) != "30")
.Skip(1) where strings.Substring(0,2) != "30"
select strings;
Это дает мне все дочерние строки «30» (но, к сожалению, пропускает саму строку «30».) Этот запрос, очевидно, потребует подзапросов для сбора и проецирования строк (с помощью выбора) в их соответствующие типы с соответствующими композициями. (ContractGroups, содержащие список групп InstrumentType и т. Д.)
Эта проблема, скорее всего, сводится к тому, что у меня нет опыта работы с функциональным программированием, поэтому, если у кого-то есть какие-либо указатели на этот вид синтаксического анализа, это было бы полезно, спасибо-