问题
+--------------+--------------+------------+
| company_name | address_type | address |
+--------------+--------------+------------+
| Company A | Billing | 111 Street |
| Company A | Shipping | 111 Street |
| Company B | Billing | 222 Street |
| Company B | Shipping | 333 street |
| Company B | Shipping | 444 street |
+--------------+--------------+------------+
I have a table similar to this.
What i need is All the companies whose billing address and shipping address are different.
NOTE - Each company has only ONE billing address. But it can have multiple Shipping addresses
This seems like a fairly simple query but I'm not just able to get it.
My attempt - I tried 'subtracting' all the shipping address from Billing but there's just no output. Distinct doesn't help as well
Query:
select company_name
from tableA
where address_type='Billing'
and company_name not in (select to_char(company_name) from tableA where address_type='Shipping');
Output should be Company B (since it's billing and shipping address is different)
EDIT 1 : Tried Indra's query but it runs forever. No response
select A.* from company A inner join company B on A.company_Name = B.company_Name
and (A.address_type = 'Billing' and B.address_type = 'Shipping')
AND A.address <> B.address
回答1:
How about using a join
? The following shows all pairs that are different:
select tb.*, ts.*
from company tb join
company ts
on tb.company_name = ts.company_name and
ts.address_type = 'shipping' and
tb.address_type = 'billing' and
ts.address <> tb.address;
If you just want the companies that are different:
select company_name
from company t
group by company_name
having count(distinct case when t.address_type = 'billing' then address end) = 1 and
count(distinct case when t.address_type = 'shipping' then address end) = 1 and
(max(case when t.address_type = 'billing' then address end) <>
max(case when t.address_type = 'shipping' then address end)
);
Note: this also checks that there is only one distinct billing and shipping address.
回答2:
Use Below Query
select A.* from company A inner join company B on A.company_Name = B.company_Name
and (A.address_type = 'Billing' and B.address_type = 'Shipping')
AND A.address <> B.address
回答3:
In this SQL Fiddle example, you can find other approach with one more company:
+--------------+--------------+------------+
| company_name | address_type | address |
+--------------+--------------+------------+
| Company A | Billing | 111 Street |
| Company A | Shipping | 111 Street |
| Company B | Billing | 222 Street |
| Company B | Shipping | 333 street |
| Company B | Shipping | 444 street |
| Company C | Shipping | 555 street |
| Company C | Shipping | 666 street |
| Company C | Billing | 555 street |
| Company C | Billing | 666 street |
+--------------+--------------+------------+
POSTDATA: SQL Fiddle works fine for me. This is all the code:
Schema:
CREATE TABLE companies
(
company_name VARCHAR2(40),
address_type VARCHAR2(40),
address VARCHAR2(40)
);
insert into companies values ('Company A','Billing','111 Street' );
insert into companies values ('Company A','Shipping','111 Street' );
insert into companies values ('Company B','Billing','222 Street' );
insert into companies values ('Company B','Shipping','333 street' );
insert into companies values ('Company B','Shipping','444 street');
insert into companies values ('Company C','Billing','555 Street' );
insert into companies values ('Company C','Billing','666 Street' );
insert into companies values ('Company C','Shipping','555 Street' );
insert into companies values ('Company C','Shipping','666 Street' );
Sentece:
SELECT DISTINCT(comp.company_name) FROM
(select company_name, address, count(*) regs
from companies
group by company_name, address) comp
WHERE MOD(comp.regs,2) = 1;
Result:
Company B
来源:https://stackoverflow.com/questions/32522604/compare-rows-and-columns-of-same-table