2011-06-08 80 views
3

我正在寫一個SQL查詢,這將返回一個特定用戶的拍賣清單失去,就像在eBay上。如何修復此SQL查詢返回不正確的值?

這是我的表:

bid_id bid_belongs_to_auction bid_from_user bid_price 
6  7      1    15.00 
8  7      2    19.00 
13  7      1    25.00 

有問題的區域是這樣的(從我的完整的查詢採取放置在問題的末尾):

 AND EXISTS (
       SELECT 1 
       FROM bids x 
       WHERE x.bid_belongs_to_auction = bids.bid_belongs_to_auction 
       AND x.bid_price > bids.bid_price 
       AND x.bid_from_user <> bids.bid_from_user 
       ) 

的問題是,查詢返回出價更高的所有拍賣,但會忽略用戶的更高出價。

所以,當工作上面的查詢爲例:

bid_id bid_belongs_to_auction bid_from_user bid_price 
6  7      1    15.00 
7  7      2    18.00 

在這種情況下,用戶1返回失去了拍賣,因爲有另一個出價高於用戶出價。

但是,這裏是當查詢不起作用

bid_id bid_belongs_to_auction bid_from_user bid_price 
6  7      1    15.00 
8  7      2    19.00 
13  7      1    25.00 

在這種情況下,用戶1被錯誤地返回失去了拍賣,因爲有比的彼此競價更高了之前的出價爲,但用戶已經爲此投標了更高的出價。

如果它是重要的,這是我的完整的查詢,但我認爲這不會是解決上述問題的必要的,但我在這裏反正張貼:

$query = " 
    SELECT 
     `bid_belongs_to_auction`, 
     `auction_unixtime_expiration`, 
     `auction_belongs_to_hotel`, 
     `auction_seo_title`, 
     `auction_title`, 
     `auction_description_1` 
    FROM (
     SELECT 
     `bid_belongs_to_auction`, 
     `bid_from_user`, 
     MAX(`bid_price`) AS `bid_price`, 
     `auctions`.`auction_enabled`, 
     `auctions`.`auction_unixtime_expiration`, 
     `auctions`.`auction_belongs_to_hotel`, 
     `auctions`.`auction_seo_title`, 
     `auctions`.`auction_title`, 
     `auctions`.`auction_description_1` 
     FROM `bids` 
     LEFT JOIN `auctions` ON `auctions`.`auction_id`=`bids`.`bid_belongs_to_auction` 
     WHERE `auction_enabled`='1' AND `auction_unixtime_expiration` > '$time' AND `bid_from_user`='$userId' 
     AND EXISTS (
       SELECT 1 
       FROM bids x 
       WHERE x.bid_belongs_to_auction = bids.bid_belongs_to_auction 
       AND x.bid_price > bids.bid_price 
       AND x.bid_from_user <> bids.bid_from_user 
       ) 
     GROUP BY `bid_belongs_to_auction` 
    ) AS X 
    WHERE `bid_from_user`='$userId' 
"; 
+2

它有助於發佈DDL和INSERT語句,因此我們不必對您的查詢進行反向工程,以在我們自己的計算機上構建可比較的表。 – 2011-06-08 12:54:08

回答

2

這裏有一個不同的方法:

$query = " 
    SELECT 
     `max_bids`.`bid_belongs_to_auction`, 
     `auctions`.`auction_unixtime_expiration`, 
     `auctions`.`auction_belongs_to_hotel`, 
     `auctions`.`auction_seo_title`, 
     `auctions`.`auction_title`, 
     `auctions`.`auction_description_1` 
    FROM `auctions` 
    INNER JOIN (
     SELECT 
      `bid_belongs_to_auction`, 
      MAX(`bid_price`) AS `auction_max_bid`, 
      MAX(CASE `bid_from_user` WHEN '$userId' THEN `bid_price` END) AS `user_max_bid` 
     FROM `bids` 
     GROUP BY `bid_belongs_to_auction` 
    ) AS `max_bids` ON `auctions`.`auction_id` = `max_bids`.`bid_belongs_to_auction` 
    WHERE `auctions`.`auction_enabled`='1' 
    AND `auctions`.`auction_unixtime_expiration` > '$time' 
    AND `max_bids`.`user_max_bid` IS NOT NULL 
    AND `max_bids`.`user_max_bid` <> `max_bids`.`auction_max_bid` 
"; 

基本上,當您檢索所有的最高出價拍賣,你也檢索sp特定用戶的最高出價。下一步是將獲得的列表加入auctions表中,並對用戶的最高出價應用附加過濾條件,使其不等於拍賣的最高出價。

注意:`max_bids`.`user_max_bid` IS NOT NULL條件可能是不必要的。在SQL Server中肯定會這樣,因爲`max_bids`.`user_max_bid` <> `max_bids`.`auction_max_bid`條件會隱含非空值。我不確定在MySQL中它是否一樣。

+1

謝謝,善良的先生,這完全解決了我的問題! – 2011-06-08 19:00:26

1

未經檢驗的,但是這是怎麼了我會接近它。如果在userid上有一個索引,並且在auctionid上有一個索引,則應該執行OK。

  select OurUserInfo.auctionid, OurUserInfo.userid, 
      OurUserInfo.ourusersmaxbid, Winningbids.TopPrice 
      from 

      (

      select A.auctionid, A.userid, max(A.price) as OurUsersMaxBid 
      from auctions A where userid = ? 
      group by A.auctionid, A.userid 

      ) as OurUserInfo 


      inner join 


      (      
      -- get the current winning bids for all auctions in which our user is bidding 
      select RelevantAuctions.auctionid, max(auctions.price) as TopPrice 
      from auctions inner join    
      (
      select distinct auctionid from auctions where userid = ? -- get our user's auctions 
      ) as RelevantAuctions 
      on auctions.auctionid = RelevantAuctions.auctionid 
      group by RelevantAuctions.auctionid 


      ) as WinninBids 


      on OurUserInfo.auctionid = winningbids.auctionid 

      where WinninBids.TopPrice > OurUserInfo.ourusersmaxbid 
+1

嗯,感謝您的幫助,但不幸的是,我不夠熟練地重寫您的查詢以匹配我的數據庫/表/行。您的查詢顯然使用了一種非常不同的方法這是不正確的,只是在我的情況下無法使用。 – 2011-06-08 12:14:51

+1

我只是縮短了列的名稱,並將表格叫做AUCTIONS。其餘的內聯視圖可以被稱爲任何你喜歡的內容。 – Tim 2011-06-08 13:39:09

0

而不是

SELECT 1 
    FROM bids x 
WHERE  x.bid_belongs_to_auction = bids.bid_belongs_to_auction 
     AND x.bid_price > bids.bid_price 
     AND x.bid_from_user <> bids.bid_from_user 

試試這個:

SELECT 1 
    FROM (SELECT BID_ID, 
       BID_BELONGS_TO_AUCTION, 
       BID_FROM_USER, 
       BID_PRICE 
      FROM (SELECT BID_ID, 
         BID_BELONGS_TO_AUCTION, 
         BID_FROM_USER, 
         BID_PRICE, 
         RANK() 
         OVER (
          PARTITION BY BID_BELONGS_TO_AUCTION, BID_FROM_USER 
          ORDER BY BID_PRICE DESC) 
          MY_RANK 
        FROM BIDS) 
     WHERE MY_RANK = 1) x 
WHERE  x.bid_belongs_to_auction = bids.bid_belongs_to_auction 
     AND x.bid_price > bids.bid_price 
     AND x.bid_from_user <> bids.bid_from_user;