Oracle Grouping Not Capturing All Rows - sql

I have the following grouping query and it seems to be leaving out rows...
SELECT asscfirstname, assclastname, addeddate, COUNT(*)
FROM CLUD.masterassc
GROUP BY asscfirstname, assclastname, addeddate
having count (*) >1
order by count(*) desc;
This is my data:
asscfirstname | assclastname | addeddate
------------- ------------ ----------
john doe1 1/1/00
john doe1 1/1/00
john doe2 2/1/00
john doe2 2/1/00
john doe2 2/5/00
The query results only show john doe1. How do I get it to also include the john doe2 where the addeddate is 2/1/00 since there are two of those?

be sure you have nt hidden space try using trim()
SELECT trim(asscfirstname), trim(assclastname), trim(addeddate), COUNT(*)
FROM CLUD.masterassc
GROUP BY trim(asscfirstname), trim(assclastname), trim(addeddate)
having count (*) >1
order by count(*) desc;

A date in Oracle is actually a timestamp, but your default format doesn't show the time portion. Set the time to 00:00:00 before grouping:
SELECT asscfirstname, assclastname, trunc(addeddate), COUNT(*)
FROM CLUD.masterassc
GROUP BY asscfirstname, assclastname, trunc(addeddate)
having count (*) >1
order by count(*) desc;

Related

How to select only the most recent

Table A has ID and date and name. Each time the record is changed the first 11 digits of the Id remain the same but the final digit would increase by 1. For example
123456789110 01-01-2020 John smith
119876543210 01-01-2020 Peter Griffin
119876543211 05-01-2020 Peter Griffin
How could I write a statement that shows The iD associated with John smith as well as the most recent Id of Peter Griffin? Thanks
Yet another option is using WITH TIES
Select top 1 with ties *
From YourTable
Order by row_number() over (partition by left(id,11) order by date desc)
Why not just use max()?
select name, max(id)
from t
group by name;

Is there an analytic function for count in oracle sql

select manager, count(*) over (partition by manager) cnt
from dbtable
group by manager
This will provide me the count of manager but if I need a count of senior_manager how will I get it?
|--------------------|------------------|
| Manager |Senior_Manager |
|--------------------|------------------|
| John |Arpit |
| John |govind |
| John |olive |
| Domnic |kelvin |
| Domnic |paul |
|--------------------|------------------|
Result
John 3
Domnic 2
Your code returns "1" for all managers -- because it counts the number of rows after the group by.
If you want to count the number of rows in the table for a given manager, then you want aggregation, not analytic functions:
Select manager, count(*) as cnt
from dbtable
group by manager;
I'm not sure if this answers your question, but it at least addresses the issue that the your query does not do much that is useful.
EDIT:
For the revised question, it simply seems:
Select senior_manager, count(*) as cnt
from dbtable
group by senior_manager;
The result you wanted can be retrieved by
select manager, count(*) over (partition by manager) cnt
from dbtable
This means each manager will be associated with the count of rows in the partition where {manager} value equals that exact manager. According to the table above this is what you expect to get.
Your example:
select manager, count(*) over (partition by manager) cnt
from dbtable
group by manager
Yields the following results:
MANAGER CNT
Domnic 1
John 1
If you drop the group by, you get:
MANAGER CNT
Domnic 2
Domnic 2
John 3
John 3
John 3
Are those the counts you're looking for? If so, then you can eliminate the duplicate rows with distinct:
select distinct manager, count(*) over (partition by manager) cnt
from dbtable
Which gives:
MANAGER CNT
John 3
Domnic 2

SQL - Distribution Count

Hi I have the following table:
crm_id | customer_id
jon 12345
jon 12346
ben 12347
sam 12348
I would like to show the following:
Crm_ID count | Number of customer_ids
1 2
2 1
Basically I want to count the number crm_ids that have 1,2,3,4,5+ customer_ids.
Thanks
One approach is to aggregate twice. First, aggregate over crm_id and generate counts. Then, aggregate over those counts themselves and generate a count of counts.
SELECT
cnt AS crm_id_cnt,
COUNT(*) AS num_customer_ids
FROM
(
SELECT crm_id, COUNT(DISTINCT customer_id) AS cnt
FROM yourTable
GROUP BY crm_id
) t
GROUP BY cnt;
Have a look at a demo below, given in MySQL as you did not specify a particular database (though my answer should run on most databases I think).
Demo

SQL: select three rows for each distinct value

For each distinct Name, I want to select the first three rows with the earliest time_stamp (or smallest number in UNIXTIME). What is the correct query?
Start Table:
Name Log-in Time
-------- -----------------
Don 05:30:00
Don 05:35:32
Don 07:12:43
Don 09:52:23
Don 05:32:43
James 03:30:00
James 03:54:23
James 09:51:54
James 14:43:34
James 43:22:11
James 59:43:33
James 20:12:11
Mindy 05:32:22
Mindy 15:14:44
Caroline 10:02:22
Rebecca 20:43:32
End Table:
Name Log-in Time
-------- -----------------
Don 05:30:00
Don 05:35:32
Don 07:12:43
James 03:30:00
James 03:54:23
James 09:51:54
Mindy 05:32:22
Mindy 15:14:44
Caroline 10:02:22
Rebecca 20:43:32
WITH Table (Name, LoginTime, Row) AS
(
SELECT
Name,
LoginTime,
ROW_NUMBER() OVER (PARTITION BY Name ORDER BY LoginTime)
FROM SomeTable
)
SELECT
Name,
LoginTime
FROM Table
WHERE
Row <= 3
An ansi standard approach actually looks to work with the following:
http://www.sqlfiddle.com/#!2/b814d/15
SELECT
NAME
, LOGIN
FROM (
SELECT
test_first.NAME,
test_first.LOGIN,
COUNT(*) CNT
FROM
TABLE_NAME test_first
LEFT OUTER JOIN
TABLE_NAME test_second
ON (test_first.NAME = test_second.NAME)
WHERE
test_first.LOGIN <= test_second.LOGIN
GROUP BY
test_first.NAME, test_first.LOGIN) test_order
WHERE
test_order.CNT <= 3
ORDER BY
NAME ASC, LOGIN ASC

How to produce detail, not summary, report sorted by count(*)?

Oracle 11g:
I want results to list by highest count, then ch_id. When I use group by to get the count then I loose the granularity of the detail. Is there an analytic function I could use?
SALES
ch_id desc customer
=========================
ANAR Anari BOB
SWIS Swiss JOE
SWIS Swiss AMY
BRUN Brunost SAM
BRUN Brunost ANN
BRUN Brunost ROB
Desired Results
count ch_id customer
===========================================
3 BRUN ANN
3 BRUN ROB
3 BRUN SAM
2 SWIS AMY
2 SWIS JOE
1 ANAR BOB
Use the analytic count(*):
select * from
(
select count(*) over (partition by ch_id) cnt,
ch_id, customer
from sales
)
order by cnt desc
select total, ch_id, customer
from sales s
inner join (select count(*) total, ch_id from sales group by ch_id) b
on b.ch_id = s.chi_id
order by total, ch_id
ok - the other post that happened at the same time, using partition, is the better solution for Oracle. But this one works regardless of DB.