我有一个查询正在为现有平均值添加平均值,我缩短了为示例插入的行数,但通常我们每天多次执行5,000行。
INSERT INTO stats (impcount,
average_position,
state,
dir_id,
viz_id,
date_date,
org_id,
order_id) VALUES
('2', '1', '', '5537', '22189', '2014-11-06', '-1', '15963'),
('2', '2', '', '5624', '22020', '2014-11-06', '-1', '15963'),
('2', '3', '', '5624', '18215', '2014-11-06', '-1', '15963'),
('2', '4', '', '6153', '22071', '2014-11-06', '-1', '15963'),
('1', '9', '', '5624', '21735', '2014-11-06', '-1', '15634')
ON DUPLICATE KEY UPDATE impcount = impcount + VALUES(impcount),
average_position = VALUES(average_position) + ((((average_position * impcount)
+ ( VALUES(impcount) * VALUES(average_position)) ) / (impcount + VALUES(impcount) ))
- average_position);
表结构如下:
CREATE TABLE stats (
record_id bigint(10) NOT NULL AUTO_INCREMENT,
date_year varchar(4) DEFAULT NULL,
date_month char(2) DEFAULT NULL,
date_day char(2) DEFAULT NULL,
impcount int(10) DEFAULT NULL,
date_hour varchar(4) DEFAULT NULL,
dir_id bigint(20) unsigned DEFAULT NULL,
viz_id int(9) NOT NULL DEFAULT '0',
order_id int(3) DEFAULT '0',
date_date date NOT NULL DEFAULT '0000-00-00',
average_position double DEFAULT NULL,
state varchar(200) DEFAULT NULL,
org_id int(10) unsigned DEFAULT NULL,
PRIMARY KEY (record_id),
UNIQUE KEY viz_id (viz_id,order_id,date_date,org_id),
KEY viz_counts (viz_id,date_date,impcount,average_position,order_id),
KEY daily_counts (date_date,impcount,order_id,average_position),
KEY dir_counts (dir_id,date_date,order_id),
KEY org_id (org_id)
) ENGINE=InnoDB AUTO_INCREMENT=33499742809 DEFAULT CHARSET=latin1;
有没有人知道如何简化这一点,我并不特别理解这背后的数学,但希望有人可能会认识到它,并且知道更好/更简单/更快的方法来完成同样的事情。
impcount是每行的展示次数,average_position是每次展示位置的直接平均值。根据我的理解,这是一个滚动平均值,其中每个重复密钥更新都保持平均值准确。
答案 0 :(得分:0)
令A1和A2分别为计数N1和N2的两个平均值。然后是合并的平均值
N1 × A1 + N2 × A2
A = -----------------
N1 + N2
计数N = N1 + N2。
请注意,如果您将数据存储为 sums S1和S2并计算N1和N2,则执行此操作要容易得多。组合和为S1 + S2,组合计数为N1 + N2,平均值计算为S / N.