如何运行其值更改的多个SQL查询?

时间:2013-06-17 15:15:56

标签: sql sql-server sql-server-2008

假设我有一个亚马逊客户的数据库,他们在去年购物。它非常详细,并有列,如姓名,年龄,邮政编码,收入水平,喜欢的颜色,食物,音乐等。现在,假设我运行一个查询,以便我返回购买Book X的所有亚马逊客户。

SELECT NAME, AGE, ZIPCODE, INCOME, FAVECOLOR, FAVEFOOD, FAVEMUSIC
FROM [Amazon].[dbo].[Customers]
WHERE BOOK = "X"

此查询将返回购买Book X的大量客户。现在,我想迭代每个结果(遍历每个客户)并根据每个客户的个人年龄,邮政编码和收入创建查询。

因此,如果第一个结果是Bob,32岁,住在邮政编码90210,每年45,000美元,创建一个查询,找到像Bob一样拥有相同年龄,邮政编码和收入的所有其他人。如果第二个结果是Mary,41岁,住在邮政编码10004,每年赚55,000美元,创建一个查询,找到所有其他人,如Mary,他们拥有相同的年龄,邮政编码和收入。

如何遍历购买Book X的客户并运行其价值(年龄,邮政编码,收入)正在发生变化的多个查询?在查看结果方面,如果我能看到Bob,接下来是所有客户,比如Bob,然后是Mary,以及所有像Mary这样的客户,那就太棒了。

这在SQL中是否可行?我知道如何在C#中执行此操作(for / next循环使用if / then语句),但我是SQL新手,数据在SQL中。

我使用的是SQL Server 2008。

4 个答案:

答案 0 :(得分:1)

如果我正确理解了您的要求,那么嵌套查询应该可以胜任。这样的事情:

SELECT distinct NAME, AGE, ZIPCODE, INCOME, FAVECOLOR, FAVEFOOD, FAVEMUSIC
FROM [Amazon].[dbo].[Customers] a, (SELECT NAME, AGE, ZIPCODE, INCOME, FAVECOLOR, FAVEFOOD, FAVEMUSIC
FROM [Amazon].[dbo].[Customers]
WHERE BOOK = "X" and name = 'Bob') b
WHERE BOOK = "X" and a.age=b.age and a.zipcode= b.zipcode and a.income=b.income

编辑:通用查询将是[这将包含所有用户的列表]:

SELECT distinct NAME, AGE, ZIPCODE, INCOME, FAVECOLOR, FAVEFOOD, FAVEMUSIC
    FROM [Amazon].[dbo].[Customers] a, (SELECT distinct NAME, AGE, ZIPCODE, INCOME, FAVECOLOR, FAVEFOOD, FAVEMUSIC
    FROM [Amazon].[dbo].[Customers]
    WHERE BOOK = "X" ) b
    WHERE a.BOOK = b.book and a.age=b.age and a.zipcode= b.zipcode and a.income=b.income 
order by name

答案 1 :(得分:0)

我认为您需要两个单独的查询。第一个带回客户,一旦选择了诸如Bob之类的客户,则基于Bob的属性执行第二次查询。

一个简单的例子是具有两个网格的表单应用程序。第一个显示用户列表。当您选择其中一个用户时,将使用第二个查询的结果填充第二个网格。

第二个查询类似于:

SELECT NAME, AGE, ZIPCODE, INCOME, FAVECOLOR, FAVEFOOD, FAVEMUSIC
FROM [Amazon].[dbo].[Customers]
WHERE Age = @BobsAge AND ZipCode = @BobsZipCode AND Income = @BobsIncome

听起来你想要一个简单的自我加入:

SELECT 
    MatchingCustomers.NAME, 
    MatchingCustomers.AGE, 
    MatchingCustomers.ZIPCODE, 
    MatchingCustomers.INCOME, 
    MatchingCustomers.FAVECOLOR, 
    MatchingCustomers.FAVEFOOD, 
    MatchingCustomers.FAVEMUSIC
FROM 
    [Amazon].[dbo].[Customers] SourceCustomer
    LEFT JOIN [Amazon].[dbo].[Customers] MatchingCustomers
        ON  SourceCustomer.Age = MatchingCustomer.Age
        AND SourceCustomer.ZipCode = MatchingCustomer.ZipCode 
        AND SourceCustomer.Income = MatchingCustomer.Income 
WHERE
    SourceCustomer.Book = 'X'

如果要在单个结果集中查看所有源客户及其所有匹配项,可以删除where子句并选择数据SourceCustomer:

SELECT 
    SourceCustomer.Name SourceName,
    SourceCustomer.Age SourceAge 
    SourceCustomer.ZipCode SourceZipCode,
    SourceCustomer.Income SourceIncome,
    MatchingCustomers.NAME, 
    MatchingCustomers.AGE, 
    MatchingCustomers.ZIPCODE, 
    MatchingCustomers.INCOME, 
    MatchingCustomers.FAVECOLOR, 
    MatchingCustomers.FAVEFOOD, 
    MatchingCustomers.FAVEMUSIC
FROM 
    [Amazon].[dbo].[Customers] SourceCustomer
    LEFT JOIN [Amazon].[dbo].[Customers] MatchingCustomers
        ON  SourceCustomer.Age = MatchingCustomer.Age
        AND SourceCustomer.ZipCode = MatchingCustomer.ZipCode 
        AND SourceCustomer.Income = MatchingCustomer.Income 
WHERE
    SourceCustomer.Book = 'X'

答案 2 :(得分:0)

这样的事情可以在一个查询中完成:

;WITH cteSource as
(
    SELECT NAME, AGE, ZIPCODE, INCOME, FAVECOLOR, FAVEFOOD, FAVEMUSIC
    FROM [Amazon].[dbo].[Customers]
    WHERE BOOK = "X"
)
SELECT sr.NAME AS SrcName, cu.NAME AS LikeName
FROM [Amazon].[dbo].[Customers] AS cu
JOIN cteSource As sr
    ON  cu.AGE      = sr.AGE
    And cu.ZIPCODE  = sr.ZIPCODE
    And cu.INCOME   = sr.INCOME

答案 3 :(得分:0)

这样的事情会让你追逐相关客户,例如任意客户。 5这里,分离程度。通过正确构建JOIN,您可以执行匹配范围内收入的事情,......

with Book as (
  select Id, Name, Age, ZIPCode, Income -- ...
    from Amazon.dbo.Customers
    where Book = 'X' ),
  RelatedCustomers as (
  select C.Id, C.Name, C.Age, C.ZIPCode, C.Income, 1 as Depth -- ...
    from Amazon.dbo.Customers as C inner join
      Book as B on B.Id <> C.Id and Abs( B.Income - C.Income ) < 2000 -- and ...
  union all
  select C.Id, C.Name, C.Age, C.ZIPCode, C.Income, RC.Depth + 1-- ...
    from Amazon.dbo.Customers as C inner join
      RelatedCustomers as RC on RC.Id <> C.Id and Abs( RC.Income - C.Income ) < 2000 -- and ...
      where Depth < 5 )
  select *
    from RelatedCustomers