【问题标题】:How to fill a list of Tuple whose number of elements is determined by a variable如何填充元素数量由变量确定的元组列表
【发布时间】:2017-06-27 07:38:26
【问题描述】:

我正在尝试填充元组列表,其中元素的数量由 Enumerable 确定。 我试图遍历元组列表中的枚举:

    var items = UnitOfWork.GetAll<Table>().Where(x => tableIds.Contains(x.Id));

    var tupleList = new List<Tuple<string, string>> {

            foreach (var item in items)
            {
                new Tuple<string, string>(item.A1, item.A2),
                new Tuple<string, string>(item.A1, item.A2)
            {
    };

但这似乎是不允许的(-> 右大括号处的红色摆动线))。 从元组列表外部循环不会公开元组列表以供进一步使用。 任何帮助,将不胜感激。问候,马努

在 Tims 的建议下,我的代码现在看起来:

    public IEnumerable<EmailListModel> Get()
    {
        IIndireKatPrincipal indireKatPrincipal = identityStorage.GetPrincipal();
        var groupId = indireKatPrincipal.GroupId;
        var araIds = UnitOfWork.GetAll<UserGroup>()
                .Where(group => group.Id == groupId)
                .SelectMany(group => group.S_ARA).Select(ara => ara.Id);

        var aras = UnitOfWork.GetAll<S_ARA>().Where(x => araIds.Contains(x.Id)).AsEnumerable();

        List<Tuple<string, string>> tupleList = aras
            .Select(ara => new Tuple<string, string>(ara.IEVName, ara.IEVEmail))
            .ToList();

        var emailListModel = tupleList.Select(entity => new EmailListModel()
        {
            DisplayAddress = entity.Item1,
            EmailAddress = entity.Item2
        }).ToList();

        return emailListModel;
    }

它现在完美运行(在 var aras = ... 添加 .AsEnumerable() 之后)。

【问题讨论】:

  • 您确定错误来自这部分代码吗?我无法观察到您在 this fiddle 中描述的相同行为
  • @Icepickle:我也尝试了另一个 Enumerable,我确信它会产生正确的记录 -> 调试模式中的相同错误 -> NotSupportedException,在 LINQ to Entities 中只有无参数构造函数/支持初始化器
  • 我想您的问题中缺少此信息,但是我看不出它与您提到的错误行有什么关系
  • @Icepickle:现在我用您的 ItemDataSource 进行了尝试,但没有出现错误。所以我的 ItemDataSource (var aras = ...) 中一定有错误。我会努力的。
  • @Icepickle:我发现了问题。我必须将 .AsEnumerable() 附加到我的 ItemDataSource (var aras = ...)。

标签: c#


【解决方案1】:

您不能在collection initializer 中使用foreach。使用Select + ToList

List<Tuple<string, string>> tupleList = items
   .Select(item => new Tuple<string, string>(item.A1, item.A2))
   .ToList();

Collection initializer: 元素初始值设定项可以是简单的值、表达式或 对象初始化器

允许使用expression,但不允许使用statement(例如循环)

【讨论】:

  • 您可以将Select稍微简化为:.Select(item =&gt; Tuple.Create(item.A1, item.A2))
  • @MatthewWatson:我已经调整了 OP 的偏好以使用构造函数创建一个元组
  • 确实,但也许 OP 不知道Tuple.Create(),所以最好让他知道!
  • @MatthewWatson:通常我也会尝试提出更好的方法,但在这种情况下,这只是个人喜好问题。除了或多或少的几个字母外,使用构造函数或工厂方法没有区别。也许他喜欢类型不是从参数派生,而是在代码中可见。如果我开始建议这么小的事情(这也分散了他问题的核心问题),那么我必须在每个答案中写小说;-)
  • @TimSchmelter:我使用了您的建议 -> 没有编译错误,但运行时错误(仅支持无参数构造函数/初始化程序)。现在我被困住了。
【解决方案2】:

如果您使用的是 C#7,则可以使用新的元组语法来执行此操作:

var tupleList = items.Select(item => (item.A1, item.A2)).ToList();

...

foreach (var item in tupleList)
{
    Console.WriteLine(item.Item1);
    Console.WriteLine(item.Item2);
}

如果需要,您可以将属性名称从默认的 Item1Item2 更改为其他名称:

var tupleList = items.Select(item => (A1: item.A1, A2: item.A2)).ToList();

foreach (var item in tupleList)
{
    Console.WriteLine(item.A1);
    Console.WriteLine(item.A2);
}

【讨论】:

    猜你喜欢
    • 2013-09-08
    • 2021-02-13
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-11-02
    • 2021-12-14
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多