javascript - 合并重叠数据集

标签 javascript java json merge dataset

鉴于多个数据集可能/可能不重叠在一个或多列上,我希望将数据集动态合并在一起。

是否有库或代码片段可以以这种方式合并数据集?仅使用单个列作为键来执行此操作怎么样?

示例:使用多列作为键(BookTitle、Author)合并两个数据集

输入,数据集 1

BookTitle, Author, Publisher
title1, author1, publisher1
title2, author2, publisher2
title3, author3, publisher3

输入,数据集 2

BookTitle, Author, NumPages
title4, author4, numPages4
title7, author7, numPages7
title5, author5, numPages5
title3, author33, numPages3
title2, author2, numPages2

输出,Munged 数据集

BookTitle, Author, Publisher, NumPages
title1, author1, publisher1, _null_
title2, author2, publisher2, numPages2
title3, author3, publisher3, _null_
title4, author4, _null_, numPages4
title5, author5, _null_, numPages5
title7, author7, _null_, numPages7
title3, author33, _null_, numPages3

我做了一些研究,但没有立即产生有用的结果(主要是关于同一结构中 JSON 对象的一次性合并(即附加数据,而不是合并不同的数据集))。

我正在寻找 Java/JavaScript,使用 JSON/XML/CSV 数据(按优先顺序),但我会接受其他语言,假设这些算法可以移植。

我还将考虑接受仅在单个列上完成此操作的示例。

最佳答案

嗯,我不会真的为如此简单的东西寻找一个库。相反,请尝试自己构建解决方案。

您可以首先JSON.parse()任何字符串将它们转换为对象。然后,您可以将这两个对象传递到一个如下所示的函数中。

function mergeSets(first, second) {
    var result = first;
    second.forEach(function (item, index, array) {
        var resultIndex = contains(result, item);
        if (resultIndex === -1) {
            result.push(item);
        } else {
            result[resultIndex].numPages = item.numPages;
        }
    });
    return result;
}

请注意,mergeSets() 调用 contains(),其本质如下。

function contains(set, object) {
    var solution = -1;
    set.forEach(function (item, index, array) {
        if (item.bookTitle == object.bookTitle && item.author == object.author) {
            solution = index;
        }
    });
    return solution;
}

正如您所看到的,这确实并不难。抱歉有些变量名。这是匆忙写的。另外,您在结果集的示例中提到,您希望将不可用的字段显示为 null ,这是不合适的,因为 null 通常表示空引用。相反,我忽略了他们。访问数组中没有这些字段的对象上的这些字段将导致未定义,这是完全合理的。

此外,以下是 fiddle 中代码的限制。您可以对其进行编辑以缓解这些限制并使其更加强大。

  1. 它与您在问题中提到的数据格式有关。要使其适用于任意集合,您可以在 for-in 循环中使用 Object.hasOwnProperty() 检查属性是否存在,并添加必要的属性以进行合并。

  2. 它无论如何都不处理集合内的重复项。

http://jsfiddle.net/x5Q5g/

编辑:哦!顺便说一句,代码是 JavaScript,数据格式可以是 JSON,前提是您使用 JSON.parse()JSON.stringify()

编辑:以下更新消除了上述第一个限制。请注意,您需要显式地传入要进行比较的 key 。

function contains(set, object, key) {
    var solution = -1;
    set.forEach(function (item, index, array) {
        if (item[key] === object[key]) {
            solution = index;
        }
    });
    return solution;
}

function mergeSets(first, second, key) {
    var result = first;
    second.forEach(function (item, index, array) {
        var resultIndex = contains(result, item, key);
        if (resultIndex === -1) {
            result.push(item);
        } else {
            result[resultIndex].numPages = item.numPages;
            for (var property in item) {
                if (item.hasOwnProperty(property)) {
                    if (!result[resultIndex].hasOwnProperty(property)) {
                        result[resultIndex].property = item.property;
                    }
                }
            }
        }
    });
    return result;
}

var solution = mergeSets(firstSet, secondSet, "bookTitle");
console.log(solution);

http://jsfiddle.net/s6HqL/

最后一个更新:以下是如何让它接受任意数量的 key 。我忘记了你需要多个关键支持。抱歉!

您需要更改以下内容。

function contains(set, object, keys) {
    var solution = -1;
    set.forEach(function (item, index, array) {
        var selfItem = item;
        var allKeys = keys.every(function (item, index, array) {
            if (selfItem[item] === object[item]) {
                return true;
            }
        });
        if (allKeys) {
            solution = index;
        }
    });
    return solution;
}

function mergeSets(first, second) {
    var result = first;
    var keys = Array.prototype.slice.call(arguments, 2);
    second.forEach(function (item, index, array) {
        var resultIndex = contains(result, item, keys);
        if (resultIndex === -1) {
            result.push(item);
        } else {
            for (var property in item) {
                if (item.hasOwnProperty(property)) {
                    if (!result[resultIndex].hasOwnProperty(property)) {
                        var hello = result[resultIndex];
                        hello[property] = item[property];
                    }
                }
            }
        }
    });
    return result;
}

var solution = mergeSets(firstSet, secondSet, "bookTitle", "author");
console.log(solution);

http://jsfiddle.net/s6HqL/3/

最后一个 fiddle 和上面的代码已经完成。没有任何引用资料!并且是通用的。可以使用任意数量的键作为参数。

关于javascript - 合并重叠数据集,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24968893/

相关文章:

javascript - 在同一个弹出按钮上使用多个模板

Javascript 过滤和排序值

c# - 如何在 ASP.NET Core 2.0 Web API 中配置和使用 Microsoft.AspNetCore.JsonPatch

javascript - 搜索时如何查看数据而不提交| Angular js

java - 将 != 与计数器控制的循环一起使用

python - 使用 python 在 mongodb 中插入推文搜索结果

JavaScript 正则表达式 : R naming conventions

javascript - 使用javascript删除字符串中的空格

java - 接收 SQLException "Login failed for user"连接到 SQL Server 2008

java - 使用 CDK 创建 ssh key 对/将其关联到 ec2 实例