Simple question on database query - java

I have been asked in an interview to write a SQL query which fetches the first three records with highest value on some column from a table. I had written a query which fetched all the records with highest value, but didn't get how exactly i can get only first three records of those.
Could you help me in this.
Thanks.

SELECT TOP 3 * FROM Table ORDER BY FieldName DESC
From here, but might be a little out of date:
Postgresql:
SELECT * FROM Table ORDER BY FieldName DESC LIMIT 3
MS SQL Server:
SELECT TOP 3 * FROM Table ORDER BY FieldName DESC
mySQL:
SELECT * FROM Table ORDER BY FieldName DESC LIMIT 3

Select Top 3....

Depending on the database engine, either
select top 3 * from table order by column desc
or
select * from table order by column desc limit 3

The syntax for TOP 3 varies widely from database to database.
Unfortunately, you need to use those constructs for the best performance.
Libraries like Hibernate help here, because they can translate a common API into the various SQL dialects.
Since you are asking about Java, it is possible to just SELECT everything from the database (with an ORDER BY), but just fetch only the first three rows. Depending on how the query needs to be executed this might be good enough (especially if no sorting on the database has to happen thanks to appropriate indexes, for example when you sort by primary key fields).
But in general, you want to go with an SQL solution.

In oracle you can also use where rownum < 4...
Also on mysql there is a Limit keyword (i think)

Related

Position Autoincrement in Talend

So i a bit lost and don t really know how to hang up this one...
Consider that i have a 2 DB table in Talend, let say firstly
A table invoices_only which has as fields, the invoiceNummer and the authors like this
Then, a table invoices_table with the field (invoiceNummer, article, quantity and price) and for one invoice, I can have many articles, for example
and through a tmap want to obtain a table invoice_table_result, with new columns, one for the article position, an one other for the total price. for the position i know that i can use something like the Numeric.sequence("s1",1,1) function, but don t know how to restart my counter when a new invoices nummer is found, and of course for the total price it is just a basic multiplication
so my result should be some thing like this
Here is a draft of my talend job, i m doing a lookup on the invoicenummer between the table invoice_only and invoices
Any Advices? thanks.
A trick I use is to do the sequence like this:
Numeric.sequence("s" + row.InvoiceNummer, 1, 1)
This way, the sequence gets incremented while you're still on the same InvoiceNummer, and a new one is started whenever a new InvoiceNummer is found.
There are two ways to achieve it,
tJavaFlex
Sql
tJavaFlex
You can compare current data with the previous data and reset the sequence value using below function,
if () {
Numeric.resetSequence(seqName, startValue);
}
Sql
Once data is loaded into the tables, create a post job and use an update query to update the records. You have to select the records and take the rank of the values. On top of the select you have to perform the update.
select invoicenumber, row_number() over(partition by invoicenumber, order by invoicenumber) from table name where -- conditions if any.
Update statements vary with respect to the database, please provide which database are you using, so that can provide the update query.
I would recommend you to achieve this through Sql

Randomizing select distinct

We use multiple databases at work, at least Oracle and MSSQL. Not sure why we have to use both but this question is about MSSQL.
There is a table, let's just call it System..DirectMapping that has a field accountID. I can't guarantee they are all numeric, but they appear to be.
So really my question is in two related parts.
First, I have to find a valid account id. That is one that is in the table. This is straight forward, but I would like to get a random one.
So I did a
select distinct accountID from System..DirectMapping
which works but they are always in the same order. I read how you could randomize something using newid() so I tried
select distinct accountID from System..DirectMapping order by newid()
but it gave me an error that when selecting distinct, the order by field must occur in the select which would not make sense here. So I tried
select accountID from
(select distinct accountID from System..DirectMapping) j
order by newid()
but it gave me a similar error about not being able to order by in views. I finally just read the whole thing into a java array and did a Collections.shuffle() but it would be better to do it from the query because then I could limit the number of results (I think like top 10..). So is there any way to do that?
I will save the second question for later.
You can do an ORDER BY in a view if you use a TOP specification:
select TOP 100 PERCENT accountID from
(select distinct accountID from System..DirectMapping) j
order by newid()

Speed up the data retrieval from Documentum via DQL

I am doing a Java project connected to Documentum and I need to retrieve data from object table. The thing is when I retrieve from 1 table I can get the answeres in max 2 seconds for each of the following tables with the following DQLs:
SELECT * FROM cosec_general
and
SELECT * FROM dm_dbo.cosec_general_view
however once I want to join those two tables together in retrieve from the result it takes 5 min to do so.
Is there any way that I can make it faster?
Here is the DQL that I use to join them I get teh columns that I need:
SELECT dm_dbo.cosec_general_view.name, dm_dbo.cosec_general_view.comp_id,
dm_dbo.cosec_general_view.bg_name, dm_dbo.cosec_general_view.incorporation_date,
dm_dbo.cosec_general_view.status, dm_dbo.cosec_general_view.country_name,
cosec_general.acl_domain, cosec_general.acl_name
FROM dm_dbo.cosec_general_view, cosec_general
There is no condition on which fields you are trying to join,
Add WHERE clause containing condition for join, like
WHERE dm_dbo.cosec_general_view.field_1=cosec_general.field_2
You are using wrong approach. In query
SELECT * FROM cosec_general
the asterisk * means return me everything. Once you loaded information to the memory object manipulation with it should be measured in milliseconds.

Unable to use SET key word in Spring JDBC and MySQL

I am trying to use below mentioned query in my spring jdbc template, but getting bad sql grammar exception. Is there any other way to fix this problem except stored procedure.
SET #row_number:=0;
SELECT * FROM(SELECT *,#row_number:=#row_number+1 AS row_number FROM COURSE
ORDER BY C_ID) As a where a.row_number BETWEEN 1 AND 1000 limit 15;
why you need #row_number in select query of COURSE? If pagination is your concern then use default mysql limit query.
SELECT * FROM COURSE limit ?,15;
pass the parameter from where user need to view 15 result set, please note it will start from 0.

What's the quickest validation query from a jdbc-pool to a specific table in SQL Server 2008

I usually use SELECT 1 as my preferred validation-query from tomcat jdbc pools, because it returns only one row with the result 1 that is very faster, but today I've found one terrible mistake:
My database only has one table with its primary key and is not nullable. This table sometimes is dropped, and then appears again by application circumstances. And that's the problem, SELECT 1 validate connection to database because it's already up but the table is missing so I get a terrible exception.
So, the solutions passes by finding one validation-query against the only table that exists in the database. And also, I need the query to be as fast as possible, because the performance in the application is one of the main objetives.
You can answer than an obvius query may be SELECT 1 FROM THE_TABLE but this query returns 1 for each row that the table has, and that's not very quick.
So, what could be the faster validation-query to this table??
EDIT
If I need to return at least one result, How should be the validation-query?
I ask this because some pool implementations, like commons-dbcp doesn't accept a query without results as a validated query.
How about this, which should validate the table exists without actually loading any data by pulling 0 rows and no actual columns.
SELECT TOP 0 1 FROM THE_TABLE
Demo: http://www.sqlfiddle.com/#!3/c670b/3
There are also built-in ways to check for the existance of objects in SQL SERVER. Here are two examples that do effectively the same thing.
select count(1) from information_schema.tables where table_name = 'THE_TABLE'
select OBJECT_ID('THE_TABLE') is not null

Categories