根据MAX(列名)选择和连接多个表中的行

时间:2017-02-27 22:34:49

标签: sql firebird greatest-n-per-group

总体而言,我的目标是从三个表中获取客户的电子邮件,代码和最近的奖励余额。

这三个表是:Customer,CustomerCode和Rewards

表格大致如下......

客户

#include <stdio.h>
#include <ctype.h>
void safer_gets (char array[], int max_chars);

main()
{

    /* Declare variables */
    /* ----------------- */
    char  text[51];
    char *s1_ptr = text;
    int   i;

    /* Prompt user for line of text */
    /* ---------------------------- */
    printf ("\nEnter a line of text (up to 50 characters):\n");
    safer_gets(text ,50);


    /* Convert and output the text in uppercase characters. */
    /* ---------------------------------------------------- */
    printf ("\nThe line of text in uppercase is:\n");
    while (*s1_ptr != '\0') 
        {
            *s1_ptr = toupper(*s1_ptr);          
            putchar(toupper(*s1_ptr++));
        }

    /* Convert and output the text in lowercase characters. */
    /* ---------------------------------------------------- */
    printf ("\n\nThe line of text in lowercase is:\n");
    while (*s1_ptr != '\0') 
        {
            *s1_ptr = tolower(*s1_ptr);          
            putchar(tolower(*s1_ptr++));
        }

    /* Add carriage return and pause output */
    /* ------------------------------------ */
    printf("\n");
    getchar();
} /* end main */

/* Function safer_gets */
/* ------------------- */
void safer_gets (char array[], int max_chars)
{
    /* Declare variables. */
    /* ------------------ */
    int i;

    for (i = 0; i < max_chars; i++)
        {
            array[i] = getchar();

            /* If "this" character is the carriage return, exit loop */
            /* ----------------------------------------------------- */
            if (array[i] == '\n')
                break;
        } /* end for */

    if (i == max_chars )
        if (array[i] != '\n')
            while (getchar() != '\n');
    array[i] = '\0';
} /* end safer_gets */

CustomerCode

id   email           lastcode
----|---------------|-----------
000 |test@test.com  | 1234test
001 |test1@test.com | 5678test
002 |test2@test.com | test1234
003 |test3@test.com | test5678

奖励

id   code      customer
----|---------|---------
100 |1234test | 000
101 |5678test | 001
102 |test1234 | 002
103 |test5678 | 003

我试图收集链接回客户的所有表格中的信息。我目前正在使用以下SQL查询,但遇到了一些问题。

customercode  logdate      balance
-------------|------------|--------
100          | 01/01/2016 | 1200
101          | 04/05/2016 | 40
102          | 06/22/2016 | 130
102          | 10/14/2016 | 220
103          | 12/03/2016 | 500
103          | 01/18/2017 | 750

结果

正如您所看到的,我为同一位客户获得了多个结果,但我只希望获得每位客户的最新奖励余额。

SELECT Customer.email, Customer.lastcode, CustomerCode.id, Rewards.balance, MAX(Rewards.logdate)
FROM Customer
JOIN CustomerCode ON Customer.lastcode=CustomerCode.code
JOIN Rewards ON CustomerCode.id=Rewards.CustomerCode
GROUP BY Customer.Email, Customer.LastCode, CustomerCode.id, Rewards.Balance

有什么方法可以消除这些重复记录,只显示最近的奖励余额?

2 个答案:

答案 0 :(得分:2)

您可以使用相关的子查询或聚合:

SELECT c.email, c.lastcode, cc.id, r.balance, r.logdate
FROM Customer c JOIN
     CustomerCode cc
     ON c.lastcode = cc.code JOIN
     Rewards r
     ON cc.id = r.CustomerCode JOIN
     (SELECT r.CustomerCode, MAX(r.logdate) as max_logdate
      FROM Rewards r
      GROUP BY r.CustomerCode
     ) rr
     ON rr.CustomerCode = r.CustomerCode AND rr.max_logdate = r.logdate;

答案 1 :(得分:1)

这样吗?

{
 "error": {
  "errors": [
   {
    "domain": "global",
    "reason": "UserRegistrationIncomplete",
    "message": "User has not completed registration."
   }
  ],
  "code": 401,
  "message": "User has not completed registration."
 }
}

它比Gordon的anwser更加优化,而且更加干净恕我直言。