无法将类型void隐式转换为List

时间:2018-02-08 08:03:48

标签: c# .net

我有以下类结构:

class Child
{
    public List<ParentData> ParentData { get; set; }
}

class ParentData
{
    public string FatherName {get;set;}
    public string MotherName {get;set;}
    public List<GrandParentData> GrandParentData{ get; set; }
}

class GrandParentData
{
    public string GrandFatherName {get;set;}
    public string GrandMotherName {get;set;}
}

当我试图填写这个时:

foreach (var item in res)
{
    obj.StoryData.Add(
        new StoryData
        {
            FatherName = item.FatherName,
            MotherName = item.Description,                                                                        
            GrandParentData = new List<GrandParentData().Add(
                new GrandParentData 
                { 
                    GrandFatherName = "",
                    GrandMotherName = ""
                }
            );
        }                            
    );
}

当我尝试将数据添加到GrandParentList列表时,这给了我错误:

  

无法将类型void隐式转换为List

我是否需要更改班级结构?我应该对代码进行哪些编辑?

4 个答案:

答案 0 :(得分:7)

所以这部分是问题所在:

GrandParentData=new List<GrandParentData().Add(
    new GrandParentData { GrandFatherName = "",GrandMotherName =""});

这里有三个问题:

  • 您未关闭类型参数
  • 尽管这是对象初始化程序的一部分,但你最后得到了一个分号
  • 您正在调用Add方法,该方法返回void - 因此编译时错误

作为对最后一部分的进一步解释,忽略了您在对象初始化程序中的事实,您的代码等同于尝试编写类似的内容:

List<int> list = new List<int>().Add(1);

这是无效的,因为new List<int>().Add(1)没有返回任何内容。要明确使用Add,您需要单独声明变量:

List<int> list = new List<int>();
list.Add(1);

当然,在对象初始值设定项中不起作用,因为您需要提供单个表达式来设置属性。

解决方案是使用集合初始化程序。在我们的简单案例中:

List<int> list = new List<int> { 1 };

在更复杂的情况下,您可以这样做:

GrandParentData = new List<GrandParentData>
{ 
    new GrandParentData { GrandFatherName = "", GrandMotherName = "" }
}

或者,您可以将GrandParentData更改为只读属性,但已将其初始化,如下所示:

public List<GrandParentData> GrandParentData { get; } =
    new  List<GrandParentData>();

然后你可以写:

GrandParentData =
{ 
    new GrandParentData { GrandFatherName = "", GrandMotherName = "" }
}

...并且新GrandParentData将添加到现有集合中。

答案 1 :(得分:4)

您无法创建新列表,然后以这种方式(分配值)调用Add

  • 而不是:

    GrandParentData = new List<GrandParentData>().Add(...)
    
  • 写入(使用集合初始化程序语法):

    GrandParentData = new List<GrandParentData> { new GrandParentData { ... } }
    

特定错误的原因是Add是一个void方法,因此当您尝试将结果分配给属性时,您会收到错误。

检查以下代码,看第一行是否正常,但第二行给出错误:

new List<string>().Add("text");
var list = new List<string>().Add("text");

虽然第一行实际上有效并且没有给出错误但它现在已经有了意义,因为您没有对该集合的引用,并且GC将收集初始化列表

答案 2 :(得分:2)

您正尝试将Add方法(void)的结果分配给变量。这是不可能的。 void无法分配给变量。

collection initializers来救援:

GrandParentData = new List<GrandParentData()
                  { new GrandParentData { GrandFatherName = "",GrandMotherName =""}
                  }

答案 3 :(得分:1)

问题来源是这段代码:

GrandParentData=new List<GrandParentData().Add(
new GrandParentData { GrandFatherName = "",GrandMotherName =""}
  

为什么?

GrandParentData的类型为List<GrandParentData>List<GrandParentData>.Add方法返回void,因此它只是说您无法将List<GrandParentData>映射到void返回,这是公平的。以下是List<T>.Add

的实施
 public void Add(T item) {
            if (_size == _items.Length) EnsureCapacity(_size + 1);
            _items[_size++] = item;
            _version++;
        }

检查here

解决方案是:

如上面的其他答案中所列,您在对象添加中添加对象作为创建列表的一部分,实际上您可能只是这样做:

GrandParentData = new List<GrandParentData() { new GrandParentData()}

并在构造函数中指定默认值,如下所示:

class GrandParentData
{
    public string GrandFatherName {get;set;}
    public string GrandMotherName {get;set;}

    public GrandParentData()
    {
       GrandFatherName = "";
       GrandMotherName = "";

    }
}

另一个注意事项另一个令人惊讶的问题与模型设计有关,有一个名为GrandParentData的模型,你有一个public List<GrandParentData> GrandParentData{ get; set; },这一般是令人困惑的,理想情况下使用后缀来表明它是一个集合< / p>