我需要像这样查询两个表......
表一。id companyname phone
1 | microsoft | 888-888-8888
2 | yahoo | 588-555-8874
3 | google | 225-558-4421
等...
表二 接触id companyid name phone
1 | 1 | sam | 558-998-5541
2 | 1 | john | 558-998-1154
3 | 3 | larry | 111-145-7885
4 | 3 | dave | 558-998-5254
5 | 2 | sam | 558-997-5421
我需要查询两个表。
所以,如果我搜索 sam 它应该返回一个包含联系人的公司列表
microsoft 888-888-8888
sam 558-998-5541
john 558-998-1154
yahoo 588-555-8874
sam 558-997-5421
所以它返回所有公司与山姆和所有联系人.... 同样如果我会搜索“微软”它应该返回没有雅虎
microsoft 888-888-8888
sam 558-998-5541
john 558-998-1154
如果我搜索“558-998-1154”,它应该像这样返回......
microsoft 888-888-8888
sam 558-998-5541
john 558-998-1154
我希望这很清楚......
这是我当前的查询:
SELECT * FROM
customers, customer_contacts
WHERE (customers.code LIKE '%#URL.qm1#%'
or customers.COMPANY LIKE '%#URL.qm1#%'
or customers.phone LIKE '%#URL.qm1#%'
or customers.contact LIKE '%#URL.qm1#%'
or customers.name LIKE '%#URL.qm1#%'
or customers.address1 LIKE '%#URL.qm1#%')
AND (customers.id = customer_contacts.cid
and customer_contacts.deleted = 0)
这只返回那些有联系人的人......
我需要 它也可以返回没有联系人的那些。
答案 0 :(得分:4)
这是一个棘手的问题,我几乎想说“不要试图这样做是一个查询”。
我从编程角度处理这样的SQL查询,因为我觉得结果往往不那么“神奇”。 (我在太多查询中看到的一个属性 - 现在看来SQL查询是在键盘上使用猴子编写的......)
让我们先做#2:
SELECT
companyname AS name,
phone
FROM
customers
WHERE id IN (company_ids we want)
UNION
SELECT
name, phone
FROM
contacts
WHERE companyid IN (company_ids we want)
由于“我们想要的company_ids”将成为一个查询,重新排列这个以将其简化为只发生一次:
SELECT
name, phone
FROM
(
SELECT
id AS companyid,
companyname AS name,
phone
FROM
customers
UNION
SELECT companyid, name, phone FROM contacts
) AS entities
WHERE
companyid IN (company_ids we want)
现在,要填写有趣的部分,我们需要回答#1:
第1.1部分是:
SELECT companyid FROM contacts WHERE name = $search OR number = $search;
第1.2部分是:
SELECT id AS companyid FROM customers WHERE companyname = $search OR number = $search;
(请注意,$search
是我们的输入 - 参数化查询与一个SQL供应商的差异很大,因此请根据需要替换该语法。)
将这两者中的UNION
放入IN
,我们就完成了:
SELECT
name, phone
FROM
(
SELECT
id AS companyid,
companyname AS name,
phone
FROM
customers
UNION
SELECT companyid, name, phone FROM contacts
) AS entities
WHERE
companyid IN (
SELECT companyid FROM contacts WHERE name = $search OR phone = $search
UNION
SELECT id AS companyid FROM customers WHERE companyname = $search OR phone = $search
)
;
并祈祷数据库可以找出在合理的时间内执行此操作的查询计划。当然你不想几次往返数据库?
请注意方法:我们确定了我们想要的内容(“客户/联系人的姓名/电话与某些公司匹配”),然后找出丢失的部分(“公司ID?”)。这是因为一旦你匹配公司中的某个人(例如,山姆),你就需要来自该公司的所有人,以及该公司或具有该公司ID的所有内容。知道了,我们得到了外部查询(#2),然后我们只需要弄清楚如何确定我们感兴趣的公司。
请注意,这些不会(和SQL查询,没有ORDER BY)不会以相当奇特的顺序返回查询。但是,您可以向内部查询添加帮助列,并完成此操作:
SELECT
name, phone
FROM
(
SELECT
0 AS is_person,
id AS companyid,
companyname AS name,
phone
FROM
customers
UNION
SELECT 1 AS is_person, companyid, name, phone FROM contacts
) AS entities
WHERE
companyid IN (
SELECT companyid FROM contacts WHERE name = $search OR phone = $search
UNION
SELECT id AS companyid FROM customers WHERE companyname = $search OR phone = $search
)
ORDER BY
companyid, is_person, name
;
如果您需要将结果细分为获得此查询结果的任何内容,您还可以使用is_person
列(如果将其添加到SELECT
)。
(如果你最终使用这个长度的问题,请为了上帝的爱,-- comment them!
)