Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/php/233.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/mysql/60.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Php 通过mysql使用存储过程进行社交排名_Php_Mysql_Database_Database Design_Stored Procedures - Fatal编程技术网

Php 通过mysql使用存储过程进行社交排名

Php 通过mysql使用存储过程进行社交排名,php,mysql,database,database-design,stored-procedures,Php,Mysql,Database,Database Design,Stored Procedures,我正在为数据库中的项目开发一个社会排名引擎。我想我已经解决了逻辑问题(在我的头脑中),现在正在进行实现。我希望要么是“好吧,这看起来是对的”,要么是如果我完全走错了方向,“你的白痴,卸载”。以适用者为准 基本上,我有几个表设置如下(非常简化,[…]表示未显示的其他列) 现在,目标是当用户登录并对特定项目进行“投票”时,它会在投票表中添加一行,但也会使用(我假设)一个基于类似于其他社交排名网站(如reddit的“热门”和“顶级”排序算法)的算法的存储过程在后台自动更新项目排名 我自己对该问题的假设

我正在为数据库中的项目开发一个社会排名引擎。我想我已经解决了逻辑问题(在我的头脑中),现在正在进行实现。我希望要么是“好吧,这看起来是对的”,要么是如果我完全走错了方向,“你的白痴,卸载”。以适用者为准

基本上,我有几个表设置如下(非常简化,[…]表示未显示的其他列)

现在,目标是当用户登录并对特定项目进行“投票”时,它会在投票表中添加一行,但也会使用(我假设)一个基于类似于其他社交排名网站(如reddit的“热门”和“顶级”排序算法)的算法的存储过程在后台自动更新项目排名

我自己对该问题的假设/解决方案是执行以下操作:

DELIMITER //
DROP PROCEDURE IF EXISTS updateRank//
CREATE PROCEDURE updateRank(IN itemId INT())
COMMENT 'Generates a new rank and updates the Items table'
BEGIN
   DECLARE  vote_sum,published_date INT DEFAULT 0;

   SELECT COUNT(id) INTO vote_sum,
   FROM Votes
   WHERE item_id = itemId;

   SELECT date INTO published_date
   FROM Items
   WHERE id = itemId;

   SET @o  = log(max(abs(vote_sum), 1), 10);
   SET @ts = published_date - 1307557809;
   SET @r  = round(@0 + 1 * @ts / 45000, 7);

   UPDATE Items
   SET rank = @r
   WHERE id = itemId;
END;
//
delimiter ;
INSERT INTO Votes (user_id,item_id) values (:userid,:itemid ) CALL updateRank(:itemid);
然后,在我的PDO查询中添加以下内容:

DELIMITER //
DROP PROCEDURE IF EXISTS updateRank//
CREATE PROCEDURE updateRank(IN itemId INT())
COMMENT 'Generates a new rank and updates the Items table'
BEGIN
   DECLARE  vote_sum,published_date INT DEFAULT 0;

   SELECT COUNT(id) INTO vote_sum,
   FROM Votes
   WHERE item_id = itemId;

   SELECT date INTO published_date
   FROM Items
   WHERE id = itemId;

   SET @o  = log(max(abs(vote_sum), 1), 10);
   SET @ts = published_date - 1307557809;
   SET @r  = round(@0 + 1 * @ts / 45000, 7);

   UPDATE Items
   SET rank = @r
   WHERE id = itemId;
END;
//
delimiter ;
INSERT INTO Votes (user_id,item_id) values (:userid,:itemid ) CALL updateRank(:itemid);
如果这看起来很迟钝的话,那是因为我对存储过程(最好)相当生疏,而对noob(最坏)完全不了解

我的问题基本上是:有没有更好的方法?我的妻子出去吃午饭了吗?这可以在幕后完成吗(即,不在我的查询中调用过程)?我应该使用InnoDB或MyISAM作为我的主要引擎吗?我有理由想在这个特定的项目中使用InnoDB(至少有几个表),但是我读到的所有东西似乎都告诉我永远不要使用InnoDB。。。弊大于利

编辑

建议更换

SELECT COUNT(id) INTO vote_sum
FROM Votes
WHERE item_id = itemId;
有以下几点

SELECT vote_count INTO vote_sum
FROM Votes
WHERE item_id = itemId;

这更有意义吗?然后增加投票计数字段,而不是简单地更新分数?

不知道您是否知道,但有一种更简单的方法

只需将分数和VoteCount添加到项目实体

new vote:
Score = (Score*VoteCount+NewVote) / (VoteCount + 1) 
VoteCount++;
您不知道哪些用户对哪些项目进行了投票,但 可以将其添加为自己的实体

这对你的mysql来说是一个轻松的工作,因为不算

//编辑

items:
  ItemID
  ...
  VoteSum
  VoteCount
  VoteAvg (computed field, Sum/Count, index to sort fast for "five-stars")

Track of votes - to avoid double-votes and let user delete their vote.
votes:
  UserID (PK)
  ItemID (PK)
  Rating
表决时:

 insert into votes(...
 update item set VoceCount=VotCount+1,VoteSum=VoteSum+X
问候,


//t

没有必要在问题标题中包含[伪标记]。我们这里有真正的标签!好的:(我会羞愧地低下头。嗯……所以本质上,当有人“投票”时,增加VoteCount列,如果有人“未投票”或删除了他们的投票,则减少该列?即:在“项目”表中添加一个名为“投票计数”的新列。并将“选择计数(id)”替换为“从中选择投票计数…”在我的程序的第一部分?是和否。不可能删除投票wo,因为平均值是存储的全部。请参阅更新。