show data from multi column to single row - oracle

in my oracle database contained the following data
http://i1207.photobucket.com/albums/bb476/daniwarrior/data-awal.jpg
I want to display the data as shown below
http://i1207.photobucket.com/albums/bb476/daniwarrior/data-aKHIR.jpg
Whitelist column are merging whitelist_pembayaran column, whitelist_pemasan, and whitelist_jenis_iklan
Blacklist column are merging blacklist_pembayaran column, blacklist_pemasang, and blacklist_jenis_iklan
whether the query in oracle can do? if you can how to query to display data like the picture above
*)sorry I can not show pictures because my reputation is less to be able to display the image, so I provide a link to the picture

This is string aggregation within group and string concatenation.
In Oracle 11g you can:
select
id_pegawai,
listagg(whitelist_pembayaran||whitelist_pemasan||whitelist_jenis_iklan,',') within group (order by id_pegawai) as whitelist,
listagg(blacklist_pembayaran||blacklist_pemasang||blacklist_jenis_iklan,',') within group (order by id_pegawai) as blacklist
from table
group by id_pegawai;
(in Oracle <= 10g you may use wm_concat function)
But you have to deal with commas.
Below a try for withelist(for blacklist is the same code):
select
id_pegawai,
listagg(whitelist_pembayaran||decode(whitelist_pembayaran,null,null,',')||
whitelist_pemasan||decode(whitelist_pemasan,null, null, ',')||
whitelist_jenis_iklan,',')
within group (order by id_pegawai) as whitelist
from table
group by id_pegawai;
As explanation: the decode will put a comma after a field only if the field is not null. After whitelist_jenis_iklan is not needed a coma and listagg knows to deal with its comma.

Related

How to check a checkbox in Apex 18 when its value is present in other table

I have a checkbox with list of values from table a. I need them to be checked if are present in a column of table b. Do you have any ready solution please colleagues ?
Thx
Adam
See this similar question for some background info.
When you're working with a multi-value checkbox item, you want your Source Query to select a colon-delimited list of the values that you want to be checked in your checkbox. (This is true for multi-value Application Express page items in general.) E.g.
select listagg(my_column, ':') within group (order by my_column)
from TableB
where my_column is the name of the column in TableB that your values are stored in.
If you have a lot of values in TableB (enough that the listagg() above returns more than 4000 characters), you'll need a fancier query, but for most cases it'll work fine.

ORA-00979 not a Group By function error

Iam trying to select 2 values from a Table, Employee emp_name, emp_location grouping by emp_location, iam aware that the columns which are in group by function needs to be in select clause, but i would like to know whether is there any other way to get these value in a single query.
My intention is to select only one employee per location based on age.
sample query
select emp_name,emp_location
from Employee
where emp_age=25
group by emp_location
please help in this regard.
Thanks a lot for all the guys who have responded for this question. I will try to learn these windows functions as these are very handy.
The reason why this works in MySQL and not in Oracle, is because in Oracle, as well most other databases, you either need to specify a field (or expression) in the group by clause, or it has to be an aggregation which combines the values of all values in the group into a single one. For instance, this would work:
select max(emp_name),emp_location
from Employee
where emp_age=25
group by emp_location
However, it's may not the best solution. It will work if you want just the name, but you'll get into trouble when you want to have multiple fields for an employee. In that case max won't do the trick. In the query below, you might get a first name that doesn't match the last name.
select max(emp_firstname), max(emp_lastname), emp_location
from Employee
where emp_age=25
group by emp_location
On solution for this, is using a window function (analytical function). With those, you can generate a value for each record, without immediately reducing the number of records. For instance, with a windowed max function, you could select the max age for people named John, and display that value next to every John in the result, even if they don't have that age.
Some functions, like rank, dense_rank and row_number can be used to generate a number for each employee, which you can then use to filter by. In the example below, I created such a counter per location (partition by), and ordered by, in this case name and id. You can specify other fields as well, for instance if you want one name per age per location, you specify both age and location in partition by. If you want the oldest employee of each location, you can remove where emp_age=25 and order by emp_age desc instead.
select
*
from
(select
emp_name, emp_location,
dense_rank() over (partition by emp_location order by emp_name, emp_id) as emp_rank
from Employee
where emp_age=25)
where
emp_rank = 1
ORA-00979 not a Group By function error
Only aggregate functions and columns specified in the GROUP BY clause are allowed in the SELECT clause.
In that regard, Oracle follows the SQL standard closely. But, as you noticed in your comment, some other RDBMS are less strict than Oracle regarding that point. For example, to quote MySQL's documentation (emphasis mine):
MySQL extends the use of GROUP BY so that the select list can refer to nonaggregated columns not named in the GROUP BY clause. [...]
However, this is useful primarily when all values in each nonaggregated column not named in the GROUP BY are the same for each group. The server is free to choose any value from each group, so unless they are the same, the values chosen are indeterminate.
So, in the recommended use case, adding the extra columns to the GROUP BY clause will lead to the same result.
select emp_name,emp_location
-- ^^^^^^^^
-- this is *not* part of the ̀€`GROUP BY` clause
from Employee
where emp_state=25
group by emp_location
Maybe are you looking for:
...
group by emp_location, emp_name
select emp_name,emp_location
from Employee
where emp_age=25
group by emp_name,emp_location
or
select max(emp_name) emp_name,emp_location
from Employee
where emp_age=25
group by emp_location

Display multiple columns SQL query into PL/SQL stored procedure

I have a SQL query from which select multiple columns from "db_cache_advice". I want to create a PL/SQL stored procedure from the script.
Here is the SQL script, can someone show me a small sample from which i can pick up...
select name, size_for_estimate, size_factor, estd_physical_read_factor
from v$db_cache_advice;
If you are asking whether we can select multiple columns in pl/sql stored procedure or not..
then well yes, we can select multiple columns as well..
you have to give multiple variable list with respect to number of column you are selecting -
select name, size_for_estimate, size_factor, estd_physical_read_factor
into l_name, l_size_for_estimate, l_size_factor, l_estd_physical_read_factor
from v$db_cache_advice;
please note variable should be in sync, datatype should be match with column value fetching ...

Group by specified column in PostgreSQL

Maybe, this question is a little stupid, but I'm confused.
How to group records by specified column ? :)
Item.group(:category_id)
does't works...
It says:
ActiveRecord::StatementInvalid: PGError: ERROR: column "items.id" must appear in the GROUP BY clause or be used in an aggregate function
LINE 1: SELECT "items".* FROM "items" GROUP BY category_id
What kind of aggregate function should i use?
Please, could you provide a simple example.
You will have to define, how to group values that share the same category_id. Concatenate them? Calculate a sum?
To create comma-separated lists of values your statement could look like this:
SELECT category_id
,string_agg(col1, ', ') AS col1_list
,string_agg(col2, ', ') AS col2_list
FROM items
GROUP BY category_id
You need Postgres 9.0 or later for string_agg(col1, ', ').
In older versions you can substitute with array_to_string(array_agg(col1), ', '). More aggregate functions here.
To aggregate values in PostgreSQL is the clearly superior approach as opposed to aggregating values in the client. Postgres is very fast at this and it reduces (network) traffic.
You can use sum, avg, count or any other aggregate function. More on this topic you can find here.
But it seems that you don't really need to use SQL grouping.
Try to fetch all records and then use Array#collect function to group Items by category_id
Grouping in SQL means that the server groups one or more records from the database table into one resulting row. So, if you for example group by category_id, you might have several records matching the given category, so you can't expect the database to return all columns from the table (that's what SELECT * actually does).
Instead, when you use GROUP BY, you can SELECT only:
columns you have grouped by, and/or
aggregate functions which are performed on all the records belonging to a resulting group
Depending on what you exactly need, modify your .select accordingly.

parameter in sql query :SSRS

I am using oracleclient provider. I was wondering how do I use a parameter in the query.
select * from table A where A.a in ( parameter).
The parameter should be a multivalue parameter.
how do I create a data set?
Simple. Add the parameter to the report and make sure to check it off as multi-valued. Then in the data tab and go in and edit the query click the "..." button to edit the dataset. Under the parameters tab create a mapping parameter so it looks something like this (obviously you will have different names for your parameters):
#ids | =Parameters!ContractorIDS.Value
Then in the query tab use the coorelated sub-query like your example above. I have done this many times with SQL server and there is no reason it should not work with Oracle since SSRS is going to build an ANSI compliant SQL statement which it will pass to Oracle.
where A.myfield in (#ids)
You can't have a variable in list in oracle directly. You can however, break apart a comma seperated list into rows that can be used in your subquery. The string txt can be replaced by any number of values seperated by a comma.
select * from a where a.a in (
SELECT regexp_substr(txt,'[^,]+',1,level)
FROM (SELECT 'hello,world,hi,there' txt -- replace with parameter
FROM DUAL)
CONNECT BY LEVEL <= LENGTH (REGEXP_REPLACE (txt, '[^,]'))+1
)
The query works by first counting the number of commas that are in the text string. It does this by using a reqular expression to remove all non commas and then counts the length of the remainder.
It then uses an Oracle "trick" to return that number + 1 number of rows from the dual table. It then uses the regexp_substr function to pull out each occurence.
Firstly in SSRS with an Oracle OLEDB connection you need to use the colon, not the # symbol e.g. :parameter not #parameter but then you aren't able to do this as a multi-valued parameter, it only accepts single values. Worse, if you are using an ODBC connection you have to use the question mark by itself e.g. ? not #parameter and then the ordering of parameters becomes important, and they also cannot be multi-valued. The only ways you are left with is using an expression to construct a query (join() function for the param) or calling a stored proc.
The stored proc option is best because the SSRS can handle the parameters for stored procs to both SQL Server and Oracle very cleanly, but if that is not an option you can use this expression:
="select column1, column2, a from table A where A.a in (" + Join(Parameters!parameter.Value,", ") + ")"
Or if the parameter values are strings which need apostrophes around them:
="select column1, column2, a from table A where A.a in ('" + Join(Parameters!parameter.Value,"', '") + "')"
When you right-click on the dataset, you can select "dataset properties" and then use the fx button to edit the query as an expression, rather than using the query designer which won't let you edit it as an expression.
This expression method is limited to a maximum limit of about 1000 values but if you have that many this is the wrong way to do it anyway, you'd rather join to a table.
I don't think you can use a parameter in such a situation.
(Unless oracle and the language you're using supports array-type parameters ? )
The parameters in oracle are defined as ":parametername", so in your query you should use something like:
select * from table A where value in (:parametername)
Add the parameter to the paramaters folders in the report and mark the checkbox "Allow multiple values".
As Victor Grimaldo mentioned… below worked for me very fine. As soon as I use the :parameter in my SQL query in SSRS dataset1.. it asked me to enter the values for these parameters, for which I choose already created SSRS parameters.
SELECT * FROM table a WHERE VALUE IN (**:parametername**)
Thanks Victor.

Resources