计算具有不同成员数的组的总和的算法

Dan*_*s89 0 algorithm math

让我们从一个例子开始吧.在哈利波特,霍格沃茨有4所房子,每个房子都有学生.在我的网站上也是如此,我不知道每个房子里有多少用户.它可能是20在一个房子50在另一个房子里,100在第三和第四.

现在,每个学生都可以在网站上获得积分,并且在年底,积分最高的房子将获胜.但是"只"做一点积分是不公平的,因为拥有100名学生的房子将有更高的获胜机会,因为他们有更多的用户可以获得积分.所以我需要提出一个公平的算法.

你可以在这里看到一个例子:https://worldofpotter.dk/points 我现在要做的是将房子的所有积分相加,然后除以赚取10点以上的用户数.但这仍然不公平.

关于如何使这个计算更公平的任何想法?

我们需要考虑的事项:
*每个房子中获得积分的用户百分比
*很少有用户获得大量积分
*许多用户获得了很少的积分(这不是很难获得积分.它仍然计入房子的总积分)

链接到MySQL转储(包括用户,房屋和点):https
://worldofpotter.dk/wop_points_example.sql仅链接到CSV的点:https://worldofpotter.dk/points.csv

xen*_*ros 5

我会使用类似的东西Discounted Cumulative Gain来衡量搜索引擎的有效性.

概念如下:

FUNCTION evalHouseScore (0_INDEXED_SORTED_ARRAY scores):
    score = 0;
    FOR (int i = 0; i < scores.length; i++):
        score += scores[i]/log2(i);
    END_FOR
    RETURN score;
END_FUNCTION;
Run Code Online (Sandbox Code Playgroud)

这必须以某种方式进行修改,因为这种测量方式侧重于第一个结果.由于这是主观的,你应该决定你修改它的方式.下面我将发布一些代码,你应该尝试使用不同的值:

FUNCTION evalHouseScore (0_INDEXED_SORTED_ARRAY scores):
    score = 0;
    FOR (int i = 0; i < scores.length; i++):
        score += scores[i]/log2(i+K);
    END_FOR
    RETURN L*score;
END_FUNCTION
Run Code Online (Sandbox Code Playgroud)

考虑改变对数.

测试:

    int[] g = new int[] {758,294,266,166,157,132,129,116,111,88,83,74,62,60,60,52,43,40,28,26,25,24,18,18,17,15,15,15,14,14,12,10,9,5,5,4,4,4,4,3,3,3,2,1,1,1,1,1};
    int[] s = new int[] {612,324,301,273,201,182,176,139,130,121,119,114,113,113,106,86,77,76,65,62,60,58,57,54,54,42,42,40,36,35,34,29,28,23,22,19,17,16,14,14,13,11,11,9,9,8,8,7,7,7,6,4,4,3,3,3,3,2,2,2,2,2,2,2,1,1,1};
    int[] h = new int[] {813,676,430,382,360,323,265,235,192,170,107,103,80,70,60,57,43,41,21,17,15,15,12,10,9,9,9,8,8,6,6,6,4,4,4,3,2,2,2,1,1,1};
    int[] r = new int[] {1398,1009,443,339,242,215,210,205,177,168,164,144,144,92,85,82,71,61,58,47,44,33,21,19,18,17,12,11,11,9,8,7,7,6,5,4,3,3,3,3,2,2,2,1,1,1,1};
Run Code Online (Sandbox Code Playgroud)

输出用于不同的偏移:

1182
1543
1847
2286

904
1231
1421
1735

813
1120
1272
1557
Run Code Online (Sandbox Code Playgroud)