How to make a query not referring to the table [duplicate] - sql

I've heard people referring to this table and was not sure what it was about.

It's a sort of dummy table with a single record used for selecting when you're not actually interested in the data, but instead want the results of some system function in a select statement:
e.g. select sysdate from dual;
See http://www.adp-gmbh.ch/ora/misc/dual.html
As of 23c, Oracle supports select sysdate /* or other value */, without from dual, as has been supported in MySQL for some time already.

It is a dummy table with one element in it. It is useful because Oracle doesn't allow statements like
SELECT 3+4
You can work around this restriction by writing
SELECT 3+4 FROM DUAL
instead.

From Wikipedia
History
The DUAL table was created by Chuck Weiss of Oracle corporation to provide a table for joining in internal views:
I created the DUAL table as an underlying object in the Oracle Data Dictionary. It was never meant to be seen itself, but instead used
inside a view that was expected to be queried. The idea was that you
could do a JOIN to the DUAL table and create two rows in the result
for every one row in your table. Then, by using GROUP BY, the
resulting join could be summarized to show the amount of storage for
the DATA extent and for the INDEX extent(s). The name, DUAL, seemed
apt for the process of creating a pair of rows from just one. 1
It may not be obvious from the above, but the original DUAL table had two rows in it (hence its name). Nowadays it only has one row.
Optimization
DUAL was originally a table and the database engine would perform disk IO on the table when selecting from DUAL. This disk IO was usually logical IO (not involving physical disk access) as the disk blocks were usually already cached in memory. This resulted in a large amount of logical IO against the DUAL table.
Later versions of the Oracle database have been optimized and the database no longer performs physical or logical IO on the DUAL table even though the DUAL table still actually exists.

I think this wikipedia article may help clarify.
http://en.wikipedia.org/wiki/DUAL_table
The DUAL table is a special one-row
table present by default in all Oracle
database installations. It is suitable
for use in selecting a pseudocolumn
such as SYSDATE or USER The table has
a single VARCHAR2(1) column called
DUMMY that has a value of "X"

It's the special table in Oracle. I often use it for calculations or checking system variables. For example:
Select 2*4 from dual prints out the result of the calculation
Select sysdate from dual prints the server current date.

A utility table in Oracle with only 1 row and 1 column. It is used to perform a number of arithmetic operations and can be used generally where one needs to generate a known output.
SELECT * FROM dual;
will give a single row, with a single column named "DUMMY" and a value of "X" as shown here:
DUMMY
-----
X

Kind of a pseudo table you can run commands against and get back results, such as sysdate. Also helps you to check if Oracle is up and check sql syntax, etc.

The DUAL table is a special one-row table present by default in all Oracle database installations. It is suitable for use in selecting a pseudocolumn such as SYSDATE or USER
The table has a single VARCHAR2(1) column called DUMMY that has a value of "X"
You can read all about it in http://en.wikipedia.org/wiki/DUAL_table

DUAL is necessary in PL/SQL development for using functions that are only available in SQL
e.g.
DECLARE
x XMLTYPE;
BEGIN
SELECT xmlelement("hhh", 'stuff')
INTO x
FROM dual;
END;

More Facts about the DUAL....
http://asktom.oracle.com/pls/asktom/f?p=100:11:0::::P11_QUESTION_ID:1562813956388
Thrilling experiments done here, and more thrilling explanations by Tom

DUAL we mainly used for getting the next number from the sequences.
Syntax : SELECT 'sequence_name'.NEXTVAL FROM DUAL
This will return the one row one column value(NEXTVAL column name).

another situation which requires select ... from dual is when we want to retrieve the code (data definition) for different database objects (like TABLE, FUNCTION, TRIGGER, PACKAGE), using the built in DBMS_METADATA.GET_DDL function:
select DBMS_METADATA.GET_DDL('TABLE','<table_name>') from DUAL;
select DBMS_METADATA.GET_DDL('FUNCTION','<function_name>') from DUAL;
in is true that nowadays the IDEs do offer the capability to view the DDL of a table, but in simpler environments like SQL Plus this can be really handy.
EDIT
a more general situation: basically, when we need to use any PL/SQL procedure inside a standard SQL statement, or when we want to call a procedure from the command line:
select my_function(<input_params>) from dual;
both recipes are taken from the book 'Oracle PL/SQL Recipes' by Josh Juneau and Matt Arena

The DUAL is special one row, one column table present by default in all Oracle databases. The owner of DUAL is SYS.
DUAL is a table automatically created by Oracle Database along with the data functions. It is always used to get the operating systems functions(like date, time, arithmetic expression., etc.)
SELECT SYSDATE from dual;

It's a object to put in the from that return 1 empty row. For example:
select 1 from dual;
returns 1
select 21+44 from dual;
returns 65
select [sequence].nextval from dual;
returns the next value from the sequence.

Related

what is the corresponding query in Oracle db

I have the following query which works perfectly in postgresql:
Select 'Tom' as name
output as:
name
Tom
What should be the corresponding query in Oracle?
If I run the query in Oracle it gives an error, but is run successfully in postgresql.
Oracle doesn't allow queries without a from clause. For these kind of queries, Oracle provides a system table called dual, with one column and one row:
SELECT 'Tom' as name FROM dual
Oracle needs the from clause. In that case, you have to use the DUAL table.
select 'Tom' as name from dual;
Oracle is (afaik) unusual amongst other RMDBSs in that it enforces that if you're selecting something, you must select it from a table.
To that end, there is the DUAL table. It is a special, one row, one column table that allows you to select constants, functions etc within SQL, rather than having to write a PL/SQL procedure.
I say "special" because, since 10g, the optimizer recognises that it's different to other tables and can therefore make use of that information when generating the execution path to make it more efficient than if it was using a "normal" one column, one row table.

SQL querying multiple schemas

I am looking to run a query on several schemas in workbench. bascially, they are all symmetric , just different dates. In workbench, i can only select one of them and run the query. Is there a way to aggregate them and run the query over a selection of schemas?
EDIT:
To elaborate a bit more, I have schemas with names yyyy_mm_dd for each day. Ideally, instead of doing a union over them as suggested by Guish below, If would like a dynamic query that would be able to turn the name of the schema into a valid date and Union all of them where the date is within a defined range. Is this possible? I am using Oracle and sql workbench
I guess you are using mySql workbench.
Use an union operator.
(SELECT a FROM `schema1`.`t1` )
UNION
(SELECT a FROM `schema2`.`t1`);
Info here
You can then create a view from your query.
A thread here on querying multiple shema
In know Transact-SQL a lot more and it is similar.
SELECT ProductModelID, Name
FROM Schema1.ProductModel
UNION ALL
SELECT ProductModelID, Name
FROM Schema2.ProductModel
ORDER BY Name;

Querying Oracle with a pick list

I have an oracle database that I have read-only access (with no permission to create temporary tables). I have a pick list (in Excel) of 28000 IDs corresponding to 28000 rows in a table which has millions of records. How do I write a query to return the 28000 rows?
I tried creating a table in access and performing a join through ODBC but Access freezes/takes an incredible long time. Would I have to create a query with 28,000 items in an IN statement?
Is there anything in PL/SQL that would make it easier?
Thank you for your time and help.
-JC
What makes your 28,000 rows special?
Is there another field in the records you can use to restrict you query in a WHERE clause (or at least narrow down the millions of rows a bit)? Perhaps the ID's you're interested in fall within a certain range?
The max number of variables for an IN (.., .. ,,) type query is 1000 in Oracle 10g.
Try creating an index on the table you created in Access.
That's a painful condition to be in. One workaround is to create a view that contains all of the ids, then join to it.
The example below is Oracle.
WITH
ids AS
(
SELECT 314 ID FROM DUAL UNION ALL
SELECT 159 ID FROM DUAL UNION ALL
SELECT 265 ID FROM DUAL
)
SELECT VALUE1, VALUE2
FROM SOME_TABLE, ids
WHERE SOME_TABLE.ID = ids.ID
This basically embeds all 28000 ids, in the with clause, allowing you to do the join, without actually creating a table.
Ugly, but it should work.
The best way to do it is described here: How to put more than 1000 values into an Oracle IN clause

Is there efficient SQL to query a portion of a large table

The typical way of selecting data is:
select * from my_table
But what if the table contains 10 million records and you only want records 300,010 to 300,020
Is there a way to create a SQL statement on Microsoft SQL that only gets 10 records at once?
E.g.
select * from my_table from records 300,010 to 300,020
This would be way more efficient than retrieving 10 million records across the network, storing them in the IIS server and then counting to the records you want.
SELECT * FROM my_table is just the tip of the iceberg. Assuming you're talking a table with an identity field for the primary key, you can just say:
SELECT * FROM my_table WHERE ID >= 300010 AND ID <= 300020
You should also know that selecting * is considered poor practice in many circles. They want you specify the exact column list.
Try looking at info about pagination. Here's a short summary of it for SQL Server.
Absolutely. On MySQL and PostgreSQL (the two databases I've used), the syntax would be
SELECT [columns] FROM table LIMIT 10 OFFSET 300010;
On MS SQL, it's something like SELECT TOP 10 ...; I don't know the syntax for offsetting the record list.
Note that you never want to use SELECT *; it's a maintenance nightmare if anything ever changes. This query, though, is going to be incredibly slow since your database will have to scan through and throw away the first 300,010 records to get to the 10 you want. It'll also be unpredictable, since you haven't told the database which order you want the records in.
This is the core of SQL: tell it which 10 records you want, identified by a key in a specific range, and the database will do its best to grab and return those records with minimal work. Look up any tutorial on SQL for more information on how it works.
When working with large tables, it is often a good idea to make use of Partitioning techniques available in SQL Server.
The rules of your partitition function typically dictate that only a range of data can reside within a given partition. You could split your partitions by date range or ID for example.
In order to select from a particular partition you would use a query similar to the following.
SELECT <Column Name1>…/*
FROM <Table Name>
WHERE $PARTITION.<Partition Function Name>(<Column Name>) = <Partition Number>
Take a look at the following white paper for more detailed infromation on partitioning in SQL Server 2005.
http://msdn.microsoft.com/en-us/library/ms345146.aspx
I hope this helps however please feel free to pose further questions.
Cheers, John
I use wrapper queries to select the core query and then just isolate the ROW numbers that i wish to take from the query - this allows the SQL server to do all the heavy lifting inside the CORE query and just pass out the small amount of the table that i have requested. All you need to do is pass the [start_row_variable] and the [end_row_variable] into the SQL query.
NOTE: The order clause is specified OUTSIDE the core query [sql_order_clause]
w1 and w2 are TEMPORARY table created by the SQL server as the wrapper tables.
SELECT
w1.*
FROM(
SELECT w2.*,
ROW_NUMBER() OVER ([sql_order_clause]) AS ROW
FROM (
<!--- CORE QUERY START --->
SELECT [columns]
FROM [table_name]
WHERE [sql_string]
<!--- CORE QUERY END --->
) AS w2
) AS w1
WHERE ROW BETWEEN [start_row_variable] AND [end_row_variable]
This method has hugely optimized my database systems. It works very well.
IMPORTANT: Be sure to always explicitly specify only the exact columns you wish to retrieve in the core query as fetching unnecessary data in these CORE queries can cost you serious overhead
Use TOP to select only a limited amont of rows like:
SELECT TOP 10 * FROM my_table WHERE ID >= 300010
Add an ORDER BY if you want the results in a particular order.
To be efficient there has to be an index on the ID column.

Retrieve multiple rows from an ODBC source with a UNION query

I am retrieving multiple rows into a listview control from an ODBC source. For simple SELECTs it seems to work well with a statement attribute of SQL_SCROLLABLE. How do I do this with a UNION query (with two selects)?
The most likely server will be MS SQL Server (probably 2005). The code is C for the Win32 API.
This code sets (what I think is) a server side cursor which feeds data into the ODBC driver that roughly corresponds with the positional fetches of SQLFetchScroll, which is turn feeds the cache for the listview. (Sometimes using SQL_FETCH_FIRST or SQL_FETCH_LAST as well as):
SQLSetStmtAttr(hstmt1Fetch,
SQL_ATTR_CURSOR_SCROLLABLE,
(SQLPOINTER)SQL_SCROLLABLE,
SQL_IS_INTEGER);
SQLSetStmtAttr(hstmt1Fetch,
SQL_ATTR_CURSOR_SENSITIVITY,
(SQLPOINTER)SQL_INSENSITIVE,
SQL_IS_INTEGER);
...
retcode = SQLGetStmtAttr(hstmt1Fetch,
SQL_ATTR_ROW_NUMBER,
&CurrentRowNumber,
SQL_IS_UINTEGER,
NULL);
...
retcode = SQLFetchScroll(hstmt1Fetch, SQL_FETCH_ABSOLUTE, Position);
(The above is is a fragment from working code for a single SELECT).
Is this the best way to do it? Given that I need to retrieve the last row to get the number of rows and populate the end buffer is there a better way of doing it? (Can I use forward only scrolling?)
Assuming yes to the above, how do I achieve the same result with a UNION query?
LATE EDIT: The problem with the union query being that effectively it forces forward only scrolling which breaks SQLFetchScroll(hstmt1Fetch, SQL_FETCH_ABSOLUTE, Position). The answer is I suspect: "you can't". And it really means redesigning the DB to included either a view or a single table to replace the UNION. But I'll leave the question open in case I have missed something.
can you not define a view on the db server that does the union query for you, so from the client code it just looks like a single select?
if you can't, can you just issue the union operation as part of your select, e.g.
select some_fields from table1
union
select same_fields from table2
and treat the result as a single result set?
Have you tried using union to make a derived table ?
select * from
(select field1, field from table1
union all
slect field1, filed2 from table2) a
If the issue is just needing to get the last row to get the number of rows and caching the last few rows (I assume if there are a million items in the select that you're not populating a drop-list with all of them) then you may be able to take advantage of the ROW_NUMBER() function of SQL Server 2005
You could:
select count(*)
from (select blah UNION select blah)
to get the number of rows.
Then:
select ROW_NUMBER() as rownum,blah
from (select blah UNION select blah)
where rownum between minrow and maxrow
to just fetch the rows that you need to display/cache
But seriously folks, if you're selecting items from a million-row table, you might want to consider a different mechanism
Good luck!