为多用户可排序列表建议排名算法

时间:2012-01-13 16:13:26

标签: algorithm math ranking

我正在建立一个网站,我可以让用户拖放以订购项目列表,以便为他们的“个人视图”进行排名。他们可以选择删除项目以将其隐藏在“个人视图”中。

我的问题是如何公平地实施排名算法来确定不会惩罚新项目的共享视图的项目顺序。

如果还可以用来排列新用户在用户个人列表中显示的位置,也会有所帮助。

因此,如果出现其他用户排名很高的新项目,我们可以将其显示在我们预测用户将其排名与其他用户排名相关的位置。

我最初的想法是给用户排名的每个项目分数=用户排名列表中的位置。 (例如,如果有10个项目,则给予等级1 10分,2 9分等,对于用户隐藏的项目给予负分)。共享视图将根据总分进行排序。但是对于那些基本上没有排气的新产品来说,这不会很好,并且不会轻易上升。

那么关于可以预测新项目的公平算法的任何想法?

4 个答案:

答案 0 :(得分:1)

所以我认为我有一个有效的解决方案。通过结合我在问题评论中提到的方法和Wilson's score confidence interval for a Bernoulli parameter的下限,分数似乎符合我的期望。

所以要重新评论我的评论方法:用户项目得分=项目数+ 1 - 在项目列表/计数中排名。 (1 of 3 = 1,2 = 3 = .667,2 of of 5 = .8)。

给出整体项目分数我插入Wilson公式: (phat + z * z /(2 * n) - z * Math.sqrt((phat *(1-phat)+ z * z /(4 * n))/ n))/(1 + z * z / n)的

其中phat =得分平均值,n是排名数,z = 1.96(置信度排名为95%)。

我在Excel中模拟了一些数据并使用不同的场景,并喜欢结果。将转向实施。谢谢你的帮助

答案 1 :(得分:0)

如何实现类似于9gag排名系统的东西。您可以拥有一个显示最高排名项目的共享页面和一个投票页面,用户可以在其中查看新项目并对其进行相应排名。

答案 2 :(得分:0)

我认为重要的一点是要了解其他用户在其他项目方面的排名。

“这个项目通常排名第3”是没用的,我认为,而“正在考虑的项目(我们称之为A)排名优于项目B大部分时间”是,因为它允许您为所考虑的项目列表创建(可能是模糊的)排序。

基本上,对于用户列表中的新项,您将实现一种插入排序,其中两个元素的比较由其他人列表中的平均顺序确定。实际上,任何排序算法都可以工作,只要它依赖于在两个给定元素之间有一个顺序。

答案 3 :(得分:0)

这是我在Wilson.js中的Bernoulli参数的Wilson得分置信区间

wilson.normaldist = function(qn) {
    var b = [1.570796288, 0.03706987906, -0.0008364353589, -0.0002250947176, 0.000006841218299, 0.000005824238515, -0.00000104527497, 0.00000008360937017, -0.000000003231081277, 0.00000000003657763036, 0.0000000000006936233982];
    if (qn < 0.0 || 1.0 < qn) return 0;
    if (qn == 0.5) return 0;
    var w1 = qn;
    if (qn > 0.5) w1 = 1.0 - w1;
    var w3 = -Math.log(4.0 * w1 * (1.0 - w1));
    w1 = b[0];

    function loop(i) {
        w1 += b[i] * Math.pow(w3, i);
        if (i < b.length - 1) loop(++i);
    };
    loop(1);
    if (qn > 0.5) return Math.sqrt(w1 * w3);
    else return -Math.sqrt(w1 * w3);
}

wilson.rank = function(up_votes, down_votes) {
    var confidence = 0.95;
    var pos = up_votes;
    var n = up_votes + down_votes;
    if (n == 0) return 0;
    var z = this.normaldist(1 - (1 - confidence) / 2);
    var phat = 1.0 * pos / n;
    return ((phat + z * z / (2 * n) - z * Math.sqrt((phat * (1 - phat) + z * z / (4 * n)) / n)) / (1 + z * z / n)) * 10000;
}