以下のアップデートをご覧ください!
これが私がやりたいことです: 記事の最終更新タイムスタンプ (int として格納) を、最終更新時の人気 (これも int) と共に取得し、新しい人気と結果の傾向 (= 推定値) を計算します。前回の更新以降の単位時間あたりの人気の変化について)、記事を更新します。
問題は、DB 行に書き込まれる値が、ほとんどの場合、トレンド方程式の分子 (つまり、計算された人気) または 0 のいずれかであるということです。人気の静的な値は変化しませんが、last_update またはtime() の結果、正しい値が挿入されます。その他の奇妙な点: 更新クエリから last_update を除外すると、傾向が挿入される正しい値が得られます。last_update 列がトレンド列に影響を与えるようですが、どうすればよいかわかりません。
これは私のコードです。私は codeigniter を使用しているので、記事を取得するために activerecord を使用したことに注意してください。さらに、最初の推測はデータ型の問題だったので、ほぼすべての数値に intval() を使用しました。
$this->db->where('id', 1);
$article_query = $this->db->get('articles');
$article = $article_query->row_array();
$article['last_update'] = intval($article['last_update']);
$time = intval(time());
$new_popularity = // Calculate Popularity here (I tried with static values, doesn't affect the result) ;
$time_diff = intval(($time - $article['last_update']));
$trend = intval((($new_popularity - $article['popularity']) / $time_diff));
var_dump($trend);
$this->db->query('UPDATE `articles` SET `popularity` = '.$new_popularity.', `trend` = '.$trend.' WHERE `id` = 1 ');
var ダンプは、期待値を含む int を提供します。クエリログには、予想されるクエリも表示されます。
UPDATE `articles` SET `popularity` = 50000, `last_update` = 1374840645, `trend` = 10 WHERE `id` = 1
しかし、50000 がトレンドに挿入されます。前に述べたように、$time と $article['last_update'] の静的な値は問題を解消するので、クエリから last_update を除外します。また、ceil()、floor()、すべての単一の値でキャスト (int) を試しましたが、何も機能しません。
関連するすべての列は int(11) であり、十分な大きさである必要があります。また、トレンドの varchar を試し、それを文字列として挿入しましたが、成功しませんでした。私はこの問題に 2 日間取り組んできました。
Windows 7 で MySQL 5.5.32 を実行しています。
奇妙さをなくしてください、ありがとう!
編集:さらに明確にするために: テスト目的で $article['popularity'] を 0 に設定したため、繰り返しテストしても傾向が 0 を超えることがありませんでした。そのため、実際の差ではなく、50000 が挿入されました。
更新:これが私のコードの現在の場所です。ON UPDATE CURRENT_TIMESTAMP で last_update を TIMEZONE タイプに設定します。
$this->db->where('id', 1);
$article_query = $this->db->get('articles');
$article = $article_query->row_array();
date_default_timezone_set('Europe/Berlin');
$article['last_update'] = intval(strtotime($article['last_update']));
$time = intval(time());
$new_popularity = 50000; // Static test value
$time_diff = intval(($time - $article['last_update']));
$trend = intval((($new_popularity - 0) / $time_diff)); // Zero for testing purposes only, so that there will always be a positive trend.
var_dump($trend);
$this->db->_protect_identifiers=false;
$this->db->query('UPDATE articles SET popularity = ?, trend = ? WHERE id = ?', Array($new_popularity, $trend, 1));
クエリ ログ:
UPDATE articles SET popularity = 50000, trend = 403 WHERE id = 1
phpMyAdmin による実際の値: 人気 = 50000、傾向 = 50000。現在、php 5.4.15、mysql 5.6.11 を使用して、apache と mysql のクリーン インストールでコードを実行しています。次に、コードイグナイターをまったく使わずに試してみます...
更新:私自身の間違いです。ログを注意深く読んでおらず、次のようなことが起こっていることに気づきませんでした。
130730 17:25:48 51 Connect root@localhost on zeenr
51 Init DB zeenr
51 Query SET NAMES utf8
51 Query SET SESSION sql_mode="STRICT_ALL_TABLES"
51 Query SELECT *
FROM (`articles`)
WHERE `id` = 1
51 Query UPDATE articles SET `popularity` = 50000, `trend` = 179 WHERE `id` = 1
51 Quit
130730 17:25:49 52 Connect root@localhost on zeenr
52 Init DB zeenr
52 Query SET NAMES utf8
52 Query SET SESSION sql_mode="STRICT_ALL_TABLES"
52 Query SELECT *
FROM (`articles`)
WHERE `id` = 1
52 Query UPDATE articles SET `popularity` = 50000, `trend` = 50000 WHERE `id` = 1
52 Quit
なぜそれが起こっているのですか?私のコードにはループがまったくありません。