5 성급 등급으로 정렬하는 더 좋은 방법은 무엇입니까?
-
05-07-2019 - |
문제
5 성급 시스템을 사용하여 고객 등급별로 많은 제품을 정렬하려고합니다. 내가 설정 한 사이트에는 등급이 많지 않으며 새로운 제품을 계속 추가하므로 일반적으로 등급이 적은 몇 가지 제품이 있습니다.
평균 별 등급을 사용하려고 시도했지만 등급이 적은 경우 알고리즘이 실패합니다.
예제 3x 5 별 등급을 가진 제품은 100x 5 별 등급과 2x 2 Star 등급을 가진 제품보다 더 잘 나타납니다.
두 번째 제품이 더 많은 등급으로 인해 통계적으로 더 신뢰할 수 있기 때문에 두 번째 제품이 더 높아져서는 안됩니까?
해결책
2015 년 이전에 IMDB (Internet Movie Database)는 상위 250 영화 목록. 인용 :
상단 등급 250 타이틀을 계산하기위한 공식은 진정한 베이지안 추정:
weighted rating (WR) = (v ÷ (v+m)) × R + (m ÷ (v+m)) × C
어디:
- r = 영화의 평균 (평균)
- V = 영화에 대한 투표 수
- M = 최소 투표는 상위 250 명 (현재 25000)에 상장되어 있습니다.
- C = 전체 보고서의 평균 투표 (현재 7.0)
상위 250 명에게는 정규 유권자의 투표 만 고려됩니다.
이해하기 어렵지 않습니다. 공식은 다음과 같습니다.
rating = (v / (v + m)) * R +
(m / (v + m)) * C;
수학적으로 단순화 할 수 있습니다.
rating = (R * v + C * m) / (v + m);
변수는 다음과 같습니다.
- R - 품목 자체 등급. r은 항목의 투표의 평균입니다. (예를 들어, 항목에 투표가 없으면 R은 0입니다. 누군가가 별 5 개를 주면 R이 5가됩니다. 다른 사람이 1 개의 별을 주면 R은 3이됩니다.
[1, 5]
. 등등.) - C - 평균 품목의 등급. 현재 데이터베이스를 포함하여 데이터베이스의 모든 단일 항목을 찾아 평균을 취하십시오. 즉 C (데이터베이스에 4 개의 항목이 있고 등급이
[2, 3, 5, 5]
. C는 3.75, 그 숫자의 평균입니다.) - V - 항목에 대한 투표 수. (또 다른 예를 들면, 5 명이 항목에 투표를했을 때 V는 5입니다.)
- M - 조정 가능한 매개 변수. 등급에 적용되는 "스무딩"금액은 m과 관련하여 투표 수 (v)를 기준으로합니다. 결과가 만족할 때까지 m을 조정하십시오. 그리고 "최소 투표에 필요한 최소 투표"로 IMDB의 설명을 잘못 해석하지 마십시오.
모든 공식은 다음과 같습니다. 평균을 계산하기 전에 M 상상의 투표를 각각 C 값으로 추가하십시오. 처음에는 데이터가 충분하지 않은 경우 (즉, 투표 수가 M보다 크게 적습니다), 이로 인해 빈 공간이 평균 데이터로 채워집니다. 그러나 투표가 축적됨에 따라 결국 상상의 투표는 실제 투표에 의해 익사 될 것입니다.
이 시스템에서 투표는 등급이 크게 변동하지 않습니다. 대신, 그들은 단지 그것을 어떤 방향으로 약간 교란시킵니다.
제로 투표가 있으면 상상의 투표 만 존재하며 모두 C입니다. 따라서 각 항목은 C의 등급으로 시작합니다.
또한보십시오:
다른 팁
에반 밀러가 보여줍니다 5 성급 등급 순위에 대한 베이지안 접근법 :
어디
nk
수입니다k
-스터 등급,sk
"가치"(포인트)입니다.k
별,N
총 투표 수입니다K
최대 별 수입니다 (예 : 5 성급 등급 시스템에서 K = 5)z_alpha/2
입니다1 - alpha/2
정규 분포의 양자. 실제 정렬 기준이 적어도 계산 된 정렬 기준만큼 크다는 95% 자신감 (베이지안 사후 분포에 기초)을 원한다면 선택하십시오.z_alpha/2
= 1.65.
파이썬에서 분류 기준은 다음과 같이 계산할 수 있습니다.
def starsort(ns):
"""
http://www.evanmiller.org/ranking-items-with-star-ratings.html
"""
N = sum(ns)
K = len(ns)
s = list(range(K,0,-1))
s2 = [sk**2 for sk in s]
z = 1.65
def f(s, ns):
N = sum(ns)
K = len(ns)
return sum(sk*(nk+1) for sk, nk in zip(s,ns)) / (N+K)
fsns = f(s, ns)
return fsns - z*math.sqrt((f(s2, ns)- fsns**2)/(N+K+1))
예를 들어, 품목에 60 개의 5 성급, 80 개의 4 성급, 75 개의 3 성급, 20 개의 2 성급 및 25 개의 1 성급이 있다면 전체 별 등급은 약 3.4입니다.
x = (60, 80, 75, 20, 25)
starsort(x)
# 3.3686975120774694
그리고 당신은 5 성급 등급 목록을
sorted([(60, 80, 75, 20, 25), (10,0,0,0,0), (5,0,0,0,0)], key=starsort, reverse=True)
# [(10, 0, 0, 0, 0), (60, 80, 75, 20, 25), (5, 0, 0, 0, 0)]
이것은 더 많은 등급이 전체 별 가치에 미칠 수있는 효과를 보여줍니다.
이 공식은 특히 투표권이 거의 없을 때 아마존, eBay 또는 Wal-Mart와 같은 사이트에서보고 한 전체 등급보다 약간 낮은 전체 등급을 제공하는 경향이 있음을 알 수 있습니다 (예 : 300 미만). 이것은 투표가 적은 높은 불확실성을 반영합니다. 투표 수가 증가함에 따라 (수천 명으로) 전체 전체 등급 공식은 (가중치) 평균 등급에 경향이 있어야합니다.
공식은 항목 자체에 대한 5 성급 등급의 주파수 분포에만 의존하기 때문에 쉽습니다. 결합시키다 여러 출처의 검토 (또는업데이트 단순히 주파수 분포를 함께 추가함으로써 새로운 투표에 비추어 볼 때 전체 등급.
IMDB 공식과 달리이 공식은 모든 항목의 평균 점수 나 인위적 최소 투표 수 컷오프 가치에 의존하지 않습니다.
또한이 공식은 별의 평균 수와 투표 수가 아니라 전체 주파수 분포를 사용합니다. 그리고 10 개의 5 성급과 10 개의 1 성급이있는 품목이 20 개의 3 성급 등급을 가진 품목보다 더 불확실성이있는 것으로 취급되어야한다는 것이 합리적입니다.
In [78]: starsort((10,0,0,0,10))
Out[78]: 2.386028063783418
In [79]: starsort((0,0,20,0,0))
Out[79]: 2.795342687927806
IMDB 공식은 이것을 고려하지 않습니다.
글쎄, 당신이 그것을 얼마나 복잡하게 만들고 싶은지에 따라, 당신은 사람이 만든 등급의 수와 그 등급이 무엇인지에 따라 등급에 추가로 가중치를 줄 수 있습니다. 그 사람이 하나의 등급 만 만든 경우 실리 등급 일 수 있으며 적은 비용으로 계산할 수 있습니다. 또는 그 사람이 카테고리 A에서 많은 것들을 평가했지만 카테고리 B에서는 적은 수의 등급을 받았으며 별 5 개 중 평균 등급이 1.3 인 경우 카테고리 A 가이 사용자의 낮은 평균 점수에 의해 인위적으로 무게를 측정 할 수 있습니다. 조정해야합니다.
그러나 그것을 복잡하게 만들 정도로 충분합니다. 간단하게 만들자.
우리가 특정 항목에 대해 리뷰 카운트와 평균화하는 두 가지 값으로 작업하고 있다고 가정하면 검토를 본질적으로 "신뢰성"값으로 보는 것이 합리적입니다. 그러나 우리는 낮은 리뷰 카운트 항목에 대한 점수를 낮추고 싶지 않습니다. 단일 1 성급 등급은 아마도 단일 5 성급 등급만큼 신뢰할 수 없을 것입니다. 그래서 우리가하고 싶은 것은 아마도 중간을 향한 평균입니다 : 3.
따라서 기본적으로 X * 평균 + y * 3 = the rating-we-want와 같은 방정식을 생각하고 있습니다. 이 값을 제대로 나오기 위해서는 x+y가 동일하게 필요합니다. 또한 검토 수가 증가함에 따라 값이 증가하려면 x가 필요합니다 ... 검토 수는 0이면 x는 0이어야합니다 (우리에게“방정식을 제공해야합니다. 3”), 무한 검토 카운트 X는 1이어야합니다 (이는 방정식 = 평균을 만듭니다).
그렇다면 X와 Y 방정식은 무엇입니까? x 방정식의 경우 독립 변수가 무한대에 접근함에 따라 종속 변수가 무증상으로 접근하기를 원합니다. 좋은 방정식 세트는 다음과 같습니다.
그런 다음 원하는 범위에 맞게 "요인"을 조정할 수 있습니다.
이 간단한 C# 프로그램을 사용하여 몇 가지 요소를 시도했습니다.
// We can adjust this factor to adjust our curve.
double factor = 1.5;
// Here's some sample data
double RatingAverage1 = 5;
double RatingCount1 = 1;
double RatingAverage2 = 4.5;
double RatingCount2 = 5;
double RatingAverage3 = 3.5;
double RatingCount3 = 50000; // 50000 is not infinite, but it's probably plenty to closely simulate it.
// Do the calculations
double modfactor = Math.Pow(factor, RatingCount1);
double modRating1 = (3 / modfactor)
+ (RatingAverage1 * (1 - 1 / modfactor));
double modfactor2 = Math.Pow(factor, RatingCount2);
double modRating2 = (3 / modfactor2)
+ (RatingAverage2 * (1 - 1 / modfactor2));
double modfactor3 = Math.Pow(factor, RatingCount3);
double modRating3 = (3 / modfactor3)
+ (RatingAverage3 * (1 - 1 / modfactor3));
Console.WriteLine(String.Format("RatingAverage: {0}, RatingCount: {1}, Adjusted Rating: {2:0.00}",
RatingAverage1, RatingCount1, modRating1));
Console.WriteLine(String.Format("RatingAverage: {0}, RatingCount: {1}, Adjusted Rating: {2:0.00}",
RatingAverage2, RatingCount2, modRating2));
Console.WriteLine(String.Format("RatingAverage: {0}, RatingCount: {1}, Adjusted Rating: {2:0.00}",
RatingAverage3, RatingCount3, modRating3));
// Hold up for the user to read the data.
Console.ReadLine();
그래서 당신은 그것을 복사하는 것을 귀찮게하지 않으며,이 출력을 제공합니다.
RatingAverage: 5, RatingCount: 1, Adjusted Rating: 3.67
RatingAverage: 4.5, RatingCount: 5, Adjusted Rating: 4.30
RatingAverage: 3.5, RatingCount: 50000, Adjusted Rating: 3.50
그런 것? 원하는 가중치를 얻기 위해 필요에 따라 "계수"값을 분명히 조정할 수 있습니다.
많은 계산을 사용하지 않고 주로 작동하는 빠르고 저렴한 솔루션이 필요한 경우 여기에 하나의 옵션이 있습니다 (1-5 등급 척도를 가정)
SELECT Products.id, Products.title, avg(Ratings.score), etc
FROM
Products INNER JOIN Ratings ON Products.id=Ratings.product_id
GROUP BY
Products.id, Products.title
ORDER BY (SUM(Ratings.score)+25.0)/(COUNT(Ratings.id)+20.0) DESC, COUNT(Ratings.id) DESC
25를 추가하고 총 등급 + 20으로 나누면 기본적으로 총 등급에 10 개의 최악의 점수와 10 개의 최고 점수를 추가 한 다음 그에 따라 정렬합니다.
이것은 알려진 문제가 있습니다. 예를 들어, 등급이 적은 저격수 제품에 불공평하게 보상합니다. 이 그래프 평균 점수를 가진 제품은 1.2 점을 기록한 반면 평균 점수는 1 및 1K+ 등급의 제품은 1.05에 가깝습니다. 또한 등급이 적은 고품질 제품을 부당하게 처벌한다고 주장 할 수도 있습니다.
이 차트는 1-1000 등급이 넘는 5 가지 등급 모두에 대해 어떤 일이 발생하는지 보여줍니다.http://www.wolframalpha.com/input/?i=Plot3d%5B%2825%2BXY%29/%2820%2BX%29%2C%7BX%2C1%2C1000%7D%2C%7BY%2C0%2C6% 7d%5d
당신은 바닥 등급에서 딥을 위로 볼 수 있지만, 전반적으로 그것은 공정한 순위라고 생각합니다. 이런 식으로 볼 수 있습니다.
이 그래프의 대부분의 장소에서 대리석을 떨어 뜨리면 점수가 높고 등급이 높은 제품을 자동으로 진행합니다.
분명히, 등급의 수가 적 으면이 문제는 통계 핸디캡에 있습니다. 그럼에도 불구하고...
집계 등급의 품질을 향상시키는 핵심 요소는 "평가자"를 평가하는 것입니다. 즉, 각 "평가자"가 제공 한 등급의 탭을 유지하는 것입니다 (다른 사람에 비해). 이를 통해 집계 과정에서 투표를 측정 할 수 있습니다.
또 다른 솔루션은 최종 사용자에게 기본 항목에 대한 투표의 카운트 (또는 범위 표시)를 제공하는 것입니다.
한 가지 옵션은 Microsoft의 Trueskill 시스템과 같은 것입니다. mean - 3*stddev
, 상수를 조정할 수있는 곳.
잠시 후에는 베이지안 시스템을 선택합니다. 누군가 루비를 사용하고 있다면 여기에 보석이 있습니다.
나는 Toby Segaran (Oreilly) ISBN 978-0-596-52932-1의 집단 정보를 프로그래밍하는 책을 강력히 추천하여 군중 행동에서 의미있는 데이터를 추출하는 방법을 논의합니다. 예제는 파이썬으로되어 있지만 변환하기에 쉽습니다.