Используйте DefaultIfEmpty в динамических выражениях и запросах в LINQ

Я хочу использовать динамические выражения и запросы в LINQ с предложением DefaultIfEmpty, чтобы получить все строки из двух наборов, которые не совпадают или не совпадают. Конечная цель - получить дельту соединения двух таблиц.

В таблице A I есть:

Name | Description       | Type
A    | This is something | 1
B    | Something else    | 2
C    | Where have I gone | 1

В таблице БИ есть:

Name | Description        | Type
A    | This is something  | 1
B    | Life is wonderful  | 2
D    | What happened to C | 2

Я бы хотел получить такие результаты:

Column      | Table A        | Table B
Name        | B              | B
Description | Something else | Life is wonderful
Type        | 2              | 2
---
Column      | Table A           | Table B
Name        | C                 | null
Description | Where have I gone | null
Type        | 2                 | null
---
Column      | Table A | Table B
Name        | null    | D
Description | null    | What happened to C
Type        | null    | 2

1 ответ

В этом ответе не используются динамические выражения. Однако именно решение, которое я придумал, дает мне ответ, который я ищу.

    var sql = table.SqlSelect;
    var dataLegacy = GetData(connections.Legacy, sql, table.TableName);
    var dataUpdate = GetData(connections.Update, sql, table.TableName);

    var compare = new List<CompareSet>();
    var jsonColumns = table.Json.ToList() ?? null;
    dataLegacy.AsEnumerable().ToList()
    .ForEach(legacyRow =>
    {
        DataRow updateRow = default(DataRow);
        if (table.KeyColumn.Any())
        {
            var keys = string.Join("|", table.KeyColumn.Select(kc => $"{legacyRow.Field<object>(kc)}"));
            updateRow = dataUpdate.AsEnumerable()
            .FirstOrDefault(y => keys == string.Join("|", table.KeyColumn.Select(kc => $"{y.Field<object>(kc)}")));
        }
        if (updateRow == null || JsonConvert.SerializeObject(legacyRow.ItemArray) != JsonConvert.SerializeObject(updateRow.ItemArray))
            compare.Add(new CompareSet(compare.Count, legacyRow, updateRow, jsonColumns));
    });
    dataUpdate.AsEnumerable().ToList()
    .ForEach(updateRow =>
    {
        DataRow legacyRow = default(DataRow);
        if (table.KeyColumn.Any())
        {
            var keys = string.Join("|", table.KeyColumn.Select(kc => $"{updateRow.Field<object>(kc)}"));
            legacyRow = dataLegacy.AsEnumerable()
            .FirstOrDefault(y => keys == string.Join("|", table.KeyColumn.Select(kc => $"{y.Field<object>(kc)}")));
        }
        if (legacyRow == null)
            compare.Add(new CompareSet(compare.Count, legacyRow, updateRow, jsonColumns));
    });
    if (compare.Any())
    {
        compare.OrderBy(c => c.OrderBy)
        .Dump($"{table.SchemaTable} ( {compare.Count()} / {dataLegacy.Rows.Count} / {dataUpdate.Rows.Count} rows )", TableDumpDepth);
    }
    else
    {
        "No differences found in data".Dump($"{table.SchemaTable} ( 0 / {dataLegacy.Rows.Count} / {dataUpdate.Rows.Count} rows )");
    }
Другие вопросы по тегам