Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/sql/78.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
linq到sql/xml-为链接表生成xml_Sql_Xml_Linq - Fatal编程技术网

linq到sql/xml-为链接表生成xml

linq到sql/xml-为链接表生成xml,sql,xml,linq,Sql,Xml,Linq,我有很多表和很多列,希望使用linq生成xml,而不必指定 列名。下面是一个简单的例子: users --------------- user_id name email user_addresses --------------- address_id user_id city state 这就是我想用linq生成的xml 我猜代码应该是这样的: 我可以对一个表执行此操作,但不知道如何为链接表(如用户地址)生成xml 有什么想法吗?您需要使用连接。这里有一个方法: var query = f

我有很多表和很多列,希望使用linq生成xml,而不必指定 列名。下面是一个简单的例子:

users --------------- user_id name email user_addresses --------------- address_id user_id city state 这就是我想用linq生成的xml 我猜代码应该是这样的: 我可以对一个表执行此操作,但不知道如何为链接表(如用户地址)生成xml


有什么想法吗?

您需要使用连接。这里有一个方法:

var query = from user in dc.Users
            from addr in dc.UserAddress
            where user.Id == addr.UserId
            select new XElement("user",
                new XElement("name", user.Name),
                new XElement("email", user.Email), 
                new XElement("address",
                    new XElement("city", addr.City),
                    new XElement("state", addr.State)));

foreach (var item in query)
    Console.WriteLine(item);
我有很多桌子,里面有很多 列,并希望使用 linq,而不必指定 列名


不太清楚你想如何实现这一目标。您需要说明进入XML的列名。即使要对字段名进行反思,在不指定列名的情况下,如何筛选出不需要的字段并正确地构造它们?例如,如何设置地址部分?您可以通过在User和UserAddress类上使用此选项来获取字段:User.GetType.GetFields,然后检查每个字段的名称,但接下来会发生什么?

确定找到了获取所需xml的方法,但我必须在查询中指定相关的表名……我想现在已经足够了。代码如下:

XElement root = new XElement("root",
    from row in dc.users
    where row.user_id == 5
    select new XElement("user",
        row.AsXElements(),
        new XElement("addresses",
            from row2 in dc.user_addresses
            where row2.user_id == 5
            select new XElement("address", row2.AsXElements())
        )
    )
);


// used to generate xml tags/elements named after the table column names
public static IEnumerable<XElement> AsXElements(this object source)
{
  if (source == null) throw new ArgumentNullException("source");

  foreach (System.Reflection.PropertyInfo prop in source.GetType().GetProperties())
  {
    object value = prop.GetValue(source, null);

    if (value != null)
    {
      bool isColumn = false;

      foreach (object obj in prop.GetCustomAttributes(true))
      {
        System.Data.Linq.Mapping.ColumnAttribute attribute = obj as System.Data.Linq.Mapping.ColumnAttribute;
        if (attribute != null)
        {
          isColumn = true;
          break;
        }
      }

      if (isColumn)
      {
        yield return new XElement(prop.Name, value);
      }
    }
  }
}

嘿,谢谢你的快速回复。对于我正在开发的站点,我使用xslt样式表从xml生成html。因此,使用xslt,我将指定要显示的列名,其余列名将自动过滤掉。还将处理样式表中的地址格式等。反射在从列名生成标记名方面非常有效,但我不知道如何对关联表进行同样的操作。
var query = from user in dc.Users
            from addr in dc.UserAddress
            where user.Id == addr.UserId
            select new XElement("user",
                new XElement("name", user.Name),
                new XElement("email", user.Email), 
                new XElement("address",
                    new XElement("city", addr.City),
                    new XElement("state", addr.State)));

foreach (var item in query)
    Console.WriteLine(item);
XElement root = new XElement("root",
    from row in dc.users
    where row.user_id == 5
    select new XElement("user",
        row.AsXElements(),
        new XElement("addresses",
            from row2 in dc.user_addresses
            where row2.user_id == 5
            select new XElement("address", row2.AsXElements())
        )
    )
);


// used to generate xml tags/elements named after the table column names
public static IEnumerable<XElement> AsXElements(this object source)
{
  if (source == null) throw new ArgumentNullException("source");

  foreach (System.Reflection.PropertyInfo prop in source.GetType().GetProperties())
  {
    object value = prop.GetValue(source, null);

    if (value != null)
    {
      bool isColumn = false;

      foreach (object obj in prop.GetCustomAttributes(true))
      {
        System.Data.Linq.Mapping.ColumnAttribute attribute = obj as System.Data.Linq.Mapping.ColumnAttribute;
        if (attribute != null)
        {
          isColumn = true;
          break;
        }
      }

      if (isColumn)
      {
        yield return new XElement(prop.Name, value);
      }
    }
  }
}