Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/324.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 使用Linq 2乘2行读取文件_C#_Linq - Fatal编程技术网

C# 使用Linq 2乘2行读取文件

C# 使用Linq 2乘2行读取文件,c#,linq,C#,Linq,我尝试使用Linq读取一个简单的TXT文件,但是,我的困难是。读取一个2乘2行的文件,为此,我做了一个简单的函数,但是,我相信我可以读取分隔2乘2行的TXT 我阅读文本行的代码是: private struct Test { public string Line1, Line2; }; static List<Test> teste_func(string[] args) { List<Test>

我尝试使用Linq读取一个简单的TXT文件,但是,我的困难是。读取一个2乘2行的文件,为此,我做了一个简单的函数,但是,我相信我可以读取分隔2乘2行的TXT

我阅读文本行的代码是:

    private struct Test
    {
        public string Line1, Line2;
    };

    static List<Test> teste_func(string[] args)
    {
        List<Test> exemplo = new List<Test>();
        var lines = File.ReadAllLines(args[0]).Where(x => x.StartsWith("1") || x.StartsWith("7")).ToArray();

        for(int i=0;i<lines.Length;i++)
        {
            Test aux = new Test();
            aux.Line1 = lines[i];
            i+=1;
            aux.Line2 = lines[i];

            exemplo.Add(aux);
        }

        return exemplo;
    }
但是,很明显,该系统将逐行获取,并为该行创建一个新的结构。。。 那么,我怎样才能用linq得到2乘2的直线呢

---编辑 也许有可能创建一个新的“linq”函数来实现它

Func get2line(此函数对象…){…}
像这样的东西

public static IEnumerable<B> MapPairs<A, B>(this IEnumerable<A> sequence, 
                                                 Func<A, A, B> mapper)
    {
        var enumerator = sequence.GetEnumerator();
        while (enumerator.MoveNext())
        {
            var first = enumerator.Current;
            if (enumerator.MoveNext())
            {
                var second = enumerator.Current;
                yield return mapper(first, second);
            }
            else
            {
                //What should we do with left over?
            }
        }
    }
File.ReadLines(“example.txt”)
其中(x=>x.StartsWith(“1”)| | x.StartsWith(“7”))
.Select((l,i)=>new{Index=i,Line=l})
.GroupBy(o=>o.Index/2,o=>o.Line)
.选择(g=>新测试(g));
公共结构测试
{
公共测试(IEnumerable src)
{ 
var tmp=src.ToArray();
Line1=tmp.Length>0?tmp[0]:空;
Line2=tmp.Length>1?tmp[1]:空;
}
公共字符串Line1{get;set;}
公共字符串第2行{get;set;}
}

我运行了该程序,并了解它会获得以1或7开头的行。结果作为带有2个属性的单个结构返回。我不明白“2乘2线与linq”?你想解决什么问题?您只是想将这两行连接成一行吗?如果是这样的话,只需将另一个属性添加到结构中即可。这是一个linq扩展方法,您只需要提供一个方法,该方法接受两个
a
s(如果它们是文件的行,则为字符串)并返回一个
B
(类型为
Test
)的对象@Rob它不是linq方法。它只是您编写的一个自定义扩展方法,模拟LINQ方法中的特定编程风格。LINQ只是System.LINQ命名空间中的类。请注意,您应该真正使用
ReadLines
而不是
ReadAllLines
,最好不要调用
ToList
,除非确实需要允许行流式传输,而不是急切地加载到内存中。@Servy:是-公平点。我通常会使用
ReadLines
并省略
ToList
,但我在模拟问题中的用法,其中原始示例返回一个列表。谢谢:)。。。顺便说一句,如果我有更多的行,例如7行?你的代码很有趣,但是,“新测试(g)”,不起作用,结构没有收到构造函数的参数。。。我如何使用你的方法?@Alexandre一个结构可以有一个带参数的构造函数。它不能有无参数构造函数。我把代码改为struct。如果你不喜欢构造函数,你可以将代码内联到最后一个
选择
,但对我来说这更干净。谢谢:)。。。顺便说一句,如果我有更多的行,例如7行?@Alexandre只需将行
o.Index/2
更改为
o.Index/7
,并修改测试结构及其构造函数。
Func<T> Get2Lines<T>(this Func<T> obj....) { ... }
public static IEnumerable<B> MapPairs<A, B>(this IEnumerable<A> sequence, 
                                                 Func<A, A, B> mapper)
    {
        var enumerator = sequence.GetEnumerator();
        while (enumerator.MoveNext())
        {
            var first = enumerator.Current;
            if (enumerator.MoveNext())
            {
                var second = enumerator.Current;
                yield return mapper(first, second);
            }
            else
            {
                //What should we do with left over?
            }
        }
    }
File.ReadAllLines(...)
    .Where(...)
    .MapPairs((a1,a2) => new Test() { Line1 = a1, Line2 = a2 })
    .ToList();
File.ReadLines("example.txt")
    .Where(x => x.StartsWith("1") || x.StartsWith("7"))
    .Select((l, i) => new {Index = i, Line = l})
    .GroupBy(o => o.Index / 2, o => o.Line)
    .Select(g => new Test(g));

public struct Test
{
    public Test(IEnumerable<string> src) 
    { 
        var tmp = src.ToArray();
        Line1 = tmp.Length > 0 ? tmp[0] : null;
        Line2 = tmp.Length > 1 ? tmp[1] : null;
    }

    public string Line1 { get; set; }
    public string Line2 { get; set; }
}