C# 使用linq将反序列化json展平为;“非规范化”;列表

C# 使用linq将反序列化json展平为;“非规范化”;列表,c#,linq,C#,Linq,归根结底,这只是一个基本的.net问题,但有一点背景:我正试图使用SQL Server Integration Services脚本组件从survey monkey的rest API中提取数据。因为这是在SSIS中的脚本任务中发生的,并且在GAC中注册助手库不是一个选项,所以第三方库和第三方SSIS工具都不存在。很明显,这不是一个理想的方式,但这是我现在所坚持的。我能够毫无问题地提取所需的json数据,每个数据都被反序列化为类型的对象,并添加到该类型的列表中。课程: public class S

归根结底,这只是一个基本的.net问题,但有一点背景:我正试图使用SQL Server Integration Services脚本组件从survey monkey的rest API中提取数据。因为这是在SSIS中的脚本任务中发生的,并且在GAC中注册助手库不是一个选项,所以第三方库和第三方SSIS工具都不存在。很明显,这不是一个理想的方式,但这是我现在所坚持的。我能够毫无问题地提取所需的json数据,每个数据都被反序列化为
类型的对象,并添加到该类型的列表中。课程:

public class SurveyDetail
        {
            public long? Id { get; set; }
            public string Title { get; set; }
            public string Nickname { get; set; }
            public string Category { get; set; }
            public string Language { get; set; }
            public int? Question_Count { get; set; }
            public DateTime? Date_Created { get; set; }
            public DateTime? Date_Modified { get; set; }  
            public List<Page> Pages { get; set; }             
        }

public class Page
        {
            public List<Question> Questions { get; set; }
        }

public class Question
        {
            public long? Id { get; set; }
            public string Title { get; set; }
            public QuestionFamily? Family { get; set; }
            public List<Headings> Headings { get; set; } 
            public QuestionAnswers Answers { get; set; }
        }

public class Headings
        {
            public string Heading { get; set; }
        }

public class QuestionAnswers
        {
            public List<Choice> Choices { get; set; }
        }

public class Choice
        {
            public long? Id { get; set; }
            public string Text { get; set; }      
        } 
绊脚石似乎是
中的
对象有时可能是空的,我的目标是在这种情况下
中有空值,但是在尝试这样做时,我会遇到空引用异常:

List<SurveyQuestionOption> flatData = new List<SurveyQuestionOption>();

    flatData = (from s in surveyDetails
                    from p in s.Pages
                    from q in p.Questions
                    from h in q.Headings.DefaultIfEmpty()
                    from c in q.Answers.Choices.DefaultIfEmpty()
                    select new SurveyQuestionOption
                    {
                        SurveyID = s.Id == null ? null : s.Id,
                        SurveyTitle = s.Title == null ? null : s.Title,
                        DateCreated = s.Date_Created == null ? null : s.Date_Created,
                        DateModified = s.Date_Modified == null ? null : s.Date_Modified,
                        QuestionID = q.Id == null ? null : q.Id,
                        QuestionTitle = q.Title == null ? null : q.Title,
                        QuestionType = q.Family.Value.ToString(),
                        QuestionText = h.Heading.FirstOrDefault().ToString() == null ? null : h.Heading.FirstOrDefault().ToString(),
                        AnswerOptionID = c.Id == null ? null : c.Id,
                        AnswerOptionText = c.Text == null ? null : c.Text
                    }).ToList<SurveyQuestionOption>();
List flatData=新列表();
flatData=(来自surveyDetails中的s)
来自s.页中的p
p.问题中的q
从q.headers.DefaultIfEmpty()中的h开始
来自q.Answers.Choices.DefaultIfEmpty()中的c
选择“新建调查问题”选项
{
SurveyID=s.Id==null?null:s.Id,
SurveyTitle=s.Title==null?null:s.Title,
DateCreated=s.Date\u Created==null?null:s.Date\u Created,
DateModified=s.Date\u Modified==null?null:s.Date\u Modified,
QuestionID=q.Id==null?null:q.Id,
QuestionTitle=q.Title==null?null:q.Title,
QuestionType=q.Family.Value.ToString(),
QuestionText=h.Heading.FirstOrDefault().ToString()=null?null:h.Heading.FirstOrDefault().ToString(),
AnswerOptionID=c.Id==null?null:c.Id,
AnswerOptionText=c.Text==null?null:c.Text
}).ToList();

我知道有人问过类似的问题,但我仍在努力让问题适合我的具体情况。我显然不是一个.net开发者。非常感谢任何帮助。

我能够通过为
类型的可空成员显式构造,并为DeafultIfEmpty提供一个新的
实例来解决这个问题,如下所示:

public class Question
{
    public long? Id { get; set; }
    public string Title { get; set; }
    public QuestionFamily? Family { get; set; }
    public List<Headings> Headings { get; set; }
    public string Heading { get; set; } 
    public bool? Visible { get; set; }
    public bool? ForcedRanking { get; set; }
    internal string Href { get; set; }
    public QuestionAnswers Answers { get; set; }
    public string Nickname { get; set; }

    public Question()
    {
        Answers = new QuestionAnswers();
    }
}

public class QuestionAnswers
{
    public List<Choice> Choices { get; set; }
    public OtherAnswer Other { get; set; }

    public QuestionAnswers()
    {
        Choices = new List<Choice>();
    }
}



flatData = (from s in surveyDetails
                    from p in s.Pages
                    from q in p.Questions
                    from h in q.Headings.DefaultIfEmpty()
                    from c in q.Answers.Choices.DefaultIfEmpty(new Choice())
                    select new SurveyQuestionOption
                    {
                        SurveyID = s.Id == null ? null : s.Id,
                        SurveyTitle = s.Title == null ? null : s.Title,
                        DateCreated = s.Date_Created == null ? null : s.Date_Created,
                        DateModified = s.Date_Modified == null ? null : s.Date_Modified,
                        QuestionID = q.Id == null ? null : q.Id,
                        QuestionTitle = q.Title == null ? null : q.Title,
                        QuestionType = q.Family.Value.ToString(),
                        QuestionText = h.Heading.FirstOrDefault().ToString() == null ? null : h.Heading.FirstOrDefault().ToString(),
                        AnswerOptionID = c.Id == null ? null : c.Id,
                        AnswerOptionText = c.Text == null ? null : c.Text
                    }).ToList<SurveyQuestionOption>();
公开课问题
{
公共long?Id{get;set;}
公共字符串标题{get;set;}
公共问题族?族{get;set;}
公共列表标题{get;set;}
公共字符串标题{get;set;}
公共布尔?可见{get;set;}
公共bool?ForcedRanking{get;set;}
内部字符串Href{get;set;}
公开问答{get;set;}
公共字符串昵称{get;set;}
公众问题(
{
答案=新问题答案();
}
}
公开课问答
{
公共列表选项{get;set;}
公共OtherAnswer Other{get;set;}
公众问答
{
选项=新列表();
}
}
flatData=(来自surveyDetails中的s)
来自s.页中的p
p.问题中的q
从q.headers.DefaultIfEmpty()中的h开始
从q.Answers.Choices.DefaultIfEmpty(newchoice())中的c
选择“新建调查问题”选项
{
SurveyID=s.Id==null?null:s.Id,
SurveyTitle=s.Title==null?null:s.Title,
DateCreated=s.Date\u Created==null?null:s.Date\u Created,
DateModified=s.Date\u Modified==null?null:s.Date\u Modified,
QuestionID=q.Id==null?null:q.Id,
QuestionTitle=q.Title==null?null:q.Title,
QuestionType=q.Family.Value.ToString(),
QuestionText=h.Heading.FirstOrDefault().ToString()=null?null:h.Heading.FirstOrDefault().ToString(),
AnswerOptionID=c.Id==null?null:c.Id,
AnswerOptionText=c.Text==null?null:c.Text
}).ToList();
public class Question
{
    public long? Id { get; set; }
    public string Title { get; set; }
    public QuestionFamily? Family { get; set; }
    public List<Headings> Headings { get; set; }
    public string Heading { get; set; } 
    public bool? Visible { get; set; }
    public bool? ForcedRanking { get; set; }
    internal string Href { get; set; }
    public QuestionAnswers Answers { get; set; }
    public string Nickname { get; set; }

    public Question()
    {
        Answers = new QuestionAnswers();
    }
}

public class QuestionAnswers
{
    public List<Choice> Choices { get; set; }
    public OtherAnswer Other { get; set; }

    public QuestionAnswers()
    {
        Choices = new List<Choice>();
    }
}



flatData = (from s in surveyDetails
                    from p in s.Pages
                    from q in p.Questions
                    from h in q.Headings.DefaultIfEmpty()
                    from c in q.Answers.Choices.DefaultIfEmpty(new Choice())
                    select new SurveyQuestionOption
                    {
                        SurveyID = s.Id == null ? null : s.Id,
                        SurveyTitle = s.Title == null ? null : s.Title,
                        DateCreated = s.Date_Created == null ? null : s.Date_Created,
                        DateModified = s.Date_Modified == null ? null : s.Date_Modified,
                        QuestionID = q.Id == null ? null : q.Id,
                        QuestionTitle = q.Title == null ? null : q.Title,
                        QuestionType = q.Family.Value.ToString(),
                        QuestionText = h.Heading.FirstOrDefault().ToString() == null ? null : h.Heading.FirstOrDefault().ToString(),
                        AnswerOptionID = c.Id == null ? null : c.Id,
                        AnswerOptionText = c.Text == null ? null : c.Text
                    }).ToList<SurveyQuestionOption>();