What is dual in mybatis? - sql

I am just trying to understand some old code without help which uses this mybatis statement. I did not find any proper answer. So in the below statement of myBatis what is dual?
SELECT mySeq.currVal FROM dual

Wrong question, I'd say. DUAL is related to Oracle, not MyBatis.
It is a single-row, single-column table, owned by SYS. It looks like this:
SQL> desc dual
Name Null? Type
----------------------------- -------- --------------------
DUMMY VARCHAR2(1)
SQL> select * from dual;
DUMMY
-----
X
SQL>
To users, it is available as a public synonym:
SQL> select object_name, owner, object_type
2 from all_objects
3 where object_name = 'DUAL';
OBJECT_NAME OWNER OBJECT_TYPE
-------------------- -------------------- -------------------
DUAL SYS TABLE
DUAL PUBLIC SYNONYM
SQL>
How was it created and why does it have that strange name, "dual"?
Charles Weiss:
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.
Where do we use it? Everywhere!!!
In Oracle's SQL, you have to select from something, and that's frequently dual. For example, which date is it today, or who am I?
SQL> select sysdate from dual;
SYSDATE
-------------------
04.08.2022 11:43:08
SQL> select 'My name is Littlefoot' who_am_i from dual;
WHO_AM_I
---------------------
My name is Littlefoot
SQL>
Or, in your case, you're selecting sequence's current value. Here's a demo:
Create the sequence:
SQL> create sequence myseq;
Sequence created.
Your query (won't work, though - see error description):
SQL> select myseq.currval from dual;
select myseq.currval from dual
*
ERROR at line 1:
ORA-08002: sequence MYSEQ.CURRVAL is not yet defined in this session
OK, so let's first fetch nextval:
SQL> select myseq.nextval from dual;
NEXTVAL
----------
1
Now we also have the currval:
SQL> select myseq.currval from dual;
CURRVAL
----------
1
SQL>

From the Oracle documentation:
DUAL is a table automatically created by Oracle Database along with the data dictionary. DUAL is in the schema of the user SYS but is accessible by the name DUAL to all users. It has one column, DUMMY, defined to be VARCHAR2(1), and contains one row with a value X. Selecting from the DUAL table is useful for computing a constant expression with the SELECT statement. Because DUAL has only one row, the constant is returned only once.
So that statement is querying the current value of the sequence mySeq, within your session (so there must have been a call to nextval preceding it for it to work).
In Oracle SQL you always have to select from something; dual is useful when there is no actual table you want to get data from - either for a constant or literal or function (select sysadte from dual) etc.

Related

Oracle sql data represent problem (showing 1.12455E+10 format)

I'm facing some problems while inserting and query data from the oracle SQL table. my table name is Table_Name
and it has two column names (id number, password varchar2). I make the inserting operation finely but when I query data then it as "1.14662E+10" this format.
so whats the problem is?
In SQL*Plus, You can set the format of the column to display the content of the column. For your case, You need something like this:
column your_column_name format 9999999999
The number of 9s in the above command should be the number of digits in your column's max value.
See below example(ROWNM column):
SQL> select * from T;
ROWNM NAME TOTAL COLUMN1
---------- ---------- ---------- ----------
1.2346E+17 Tejash ########## test
SQL> column rownm format 999999999999999999
SQL>
SQL> select * from T;
ROWNM NAME TOTAL COLUMN1
------------------- ---------- ---------- ----------
123456789123456789 Tejash ########## test
SQL>
The data is correctly stored and it's only a question of the way the client program (here SQL*Plus) is displaying the data.
As already answered you can use SQL*Plus formatting commands or use TO_CHAR function:
SQL> select x from t;
X
----------
1
1234567890
1.2346E+19
SQL> select to_char(x) from t;
TO_CHAR(X)
------------------------------------------------------------------------------------------------------------------------
1
1234567890
12345678901234567890
SQL>
One more trick for SQL*Plus (and SQLcl and SQL Developer) if you have several large number columns and don't want to set them all with column. There is a default display width for numbers, and beyond that size the formatting changes to scientific notation; but you can change that:
SQL> show numwidth
numwidth 10
SQL> select 12345, 123456789123456789 from dual;
12345 123456789123456789
---------- ------------------
12345 1.2346E+17
SQL> set numwidth 20
SQL> select 12345, 123456789123456789 from dual;
12345 123456789123456789
-------------------- --------------------
12345 123456789123456789
SQL>
It affects all number columns, even for smaller numbers, as you can see - so it's a broader approach and less targeted than individual column settings, but that can be useful sometimes.
You could also use set numformat to do more involved formatting, like adding group separators. Read more about set options in the documentation.

Are SCHEMA and USER the same thing in Oracle?

Are SCHEMA and USER the same thing in Oracle? Is there is situation where a single user can have two or more schemas?
Strictly speaking a SCHEMA is the set of objects owned by a USER. However, a USER can have only one SCHEMA, so people often use the terms interchangeably.
Here's the difference between USER and SCHEMA. User "A" has granted rights on its PRODUCT table to user "B". User "B" does not have a table of that name.
SQL> show user
USER is "B"
SQL> select count(*) from products
2 /
select count(*) from products
*
ERROR at line 1:
ORA-00942: table or view does not exist
SQL> select count(*) from a.product
2 /
COUNT(*)
----------
2
SQL>
Without a synonym "B" needs to prefix the schema to reference the PRODUCT table. Unless they choose to change the current schema:
SQL> alter session set current_schema = "A"
2 /
Session altered.
SQL> select count(*) from product
2 /
COUNT(*)
----------
2
SQL> show user
USER is "B"
SQL>
Now the user is "B" but the current (default) schema is "A". Which menas they need to prefix the schema when referencing their own tables!
SQL> select table_name from user_tables;
TABLE_NAME
------------------------------
YOUR_TABLE
SQL> select count(*) from your_table;
select count(*) from your_table
*
ERROR at line 1:
ORA-00942: table or view does not exist
SQL> select count(*) from b.your_table;
COUNT(*)
----------
6
SQL>
"Whether a schema can be created separately Without any user ."
No. A SCHEMA must belong to a USER. When we create user Oracle creates a schema, an empty one, automatically.
Confusingly there is a create schema syntax, but that is just a short hand for creating a number of tables (and indexes) in one statement. Find out more.

Oracle SQL - Column has no Corresponding Table

I came across something that makes no sense.
This is the SAAADMS form containing the Curriculum tab. The form has fields (columns) from different sources (tables). Most of these columns have a corresponding table, but the User ID and Activity Date (in the red rectangle) do not have a corresponding table!
You can see that the SOVLCUR_ACTIVITY_DATE and SOVLCUR_USER_ID do not have a corresponding table. It states "N/A." The other two columns I listed (I only listed a couple since there are several) do have a corresponding table.
I am trying to pull data from the two columns with no corresponding table.
The SOVLCUR table I currently have in the code does NOT exist.
How do I find where this SOVLCUR_USER_ID and SOVLCUR_ACTIVITY_DATE data is stored or pull from a column that seems to have no table?
If the data is not really stored in SOVLCUR_USER_ID and SOVLCUR_ACTIVITY_DATE is there a way for me to see where it is stored? find all associated columns?
SELECT
SP.SPRIDEN_ID AS "STUDENT_ID",
SP.SPRIDEN_LAST_NAME AS "LAST",
SP.SPRIDEN_FIRST_NAME AS "FIRST",
SD.SARADAP_TERM_CODE_ENTRY AS "TERM",
SD.SARADAP_APPL_DATE AS "APP_DATE",
SV.SOVLCUR_USER_ID AS "USER_ID", /*SOVLCUR table does not exist*/
SV.SOVLCUR_ACTIVITY_DATE AS "ACTIVITY_DATE", /*SOVLCUR table does not exist*/
SYSDATE
FROM
SPRIDEN SP
JOIN SARADAP SD
ON SPRIDEN_PIDM = SARADAP_PIDM
JOIN SOVLCUR SV /*This table does not exist*/
ON SPRIDEN_PIDM = SOVLCUR_PIDM
WHERE
SP.SPRIDEN_CHANGE_IND IS NULL
AND
SD.SARADAP_TERM_CODE_ENTRY >= '201510'
AND
SV.SOVLCUR_USER_ID NOT IN ('SSmith', 'JJones')
AND
SV.SOVLCUR_ACTIVITY_DATE BETWEEN SYSDATE-1 AND SYSDATE
Oracle provides views/tables that can be query to find out that type of information:
select table_name from all_tab_columns
where column_name = 'COLUMN NAME';
This query will return all the table where that column exists.
As user1261620 said, use ALL_TAB_COLUMNS to see the table_name corresponding to a column_name. But, as you say that few tables does not exist, perhaps, those are not tables, rather VIEWS.
To confirm whether those are TABLE or VIEW, you can query ALL_OBJECTS
SELECT object_name, object_type
FROM all_objects
WHERE object_name = 'SOVLCUR';
If the above returns no rows, that would mean the object really doesn't exist. But, in that case the query won't be executed, as it won't be parsed at all. You would get error : table/view does not exist`.
Also, not all values needs to be always stored in database. The computed values are generally calculated through a query and returned to the user for display. And other than computed values, few static values like SYSDATE can be dynamically generated rather than storing it in database and querying it.
So, I think, those are not tables, rather VIEWS. Follow the steps as I mentioned to have a clear understanding.
Update Based on OP's new inputs
So, now you know that SOVLCUR is a synonym. Execute the following query to see its details :
SELECT * FROM all_synonyms WHERE synonym_name = 'SOVLCUR';
For example,
I am user LALIT, and I create a synonym for EMP table in SCOTT schema.
SQL> show USER
USER is "LALIT"
SQL>
SQL> CREATE OR REPLACE SYNONYM lalit FOR scott.emp
2 /
Synonym created.
SQL>
SQL> SELECT owner, synonym_name, table_owner, table_name
2 FROM all_synonyms
3 WHERE synonym_name = 'LALIT'
4 /
OWNER SYNONYM_NAME TABLE_OWNER TABLE_NAME
---------- --------------- ------------ ----------
LALIT LALIT SCOTT EMP
So, the table_owner and table_name shows the SCHEMA is SCOTT and TABLE is EMP.

About dual table structure in Oracle SQL *Plus

We know that "Dual" is a temporary table which exactly contains 1 column whose name is "dummy" which is of "varchar2(1)" type that has 1 single row. The value of that record is "X". The varchar2 has size of 1 which means it should not allow more than a single character.
Now my question is: If it is of varchar2 type, then why it can hold any datatype temporarily AND If we insert characters more than 1 (size), how this is possible for it (dual) to accept it ? Example:
SQL> desc dual
Name Null? Type
------------------------------- -------- ----
DUMMY VARCHAR2(1)
SQL> select sysdate from dual;
SYSDATE
---------
22-JAN-13
SQL> select 5*5 result from dual;
RESULT
---------
25
SQL> select 'Ankita' as "Name" from dual;
Name
------
Ankita
Clearly "SYSDATE" is of DATE type (not varchar2), "RESULT" is of NUMBER type (not varchar2). Also 'Ankita' is more than 1 single character, i.e., 6 characters. This should contradict the structure that varchar2 is holding only 1, and supporting 6 too..
The types and sizes of columns only come into play when you extract the data from them. It's true that if you select the dummy column, it will only give you what is in that column.
But, when you're selecting something unrelated to the column data, such as 5*5 or 'Ankita', they have no such restrictions.
I think your misunderstanding stems from your snippet:
why it can hold any datatype temporarily AND If we insert characters more than 1 (size), how this is possible for it (dual) to accept it ?
The truth is, the column doesn't accept it. Selecting 5*5 does not attempt to place that data into the table somewhere, it just evaluates it as-is. It's no different to having a table with:
users:
id
name
and performing:
select 42, 3.14159, id, name from users
For every row selected from, you will see the constant values 42 and 3.14159, alongside the data extracted from the two specified columns.

pseudo columns & DUAL table - what do they actually mean?

Dual table is used to select pseudo columns.
it has one row and one column DUMMY which has a value X.
I have two questions
What actually does a pseudo
column mean?
How is the dual able to give the
value for example:
select sysdate from dual
will result in current datetime. How is this possible?
A pseudo-column is a function which returns a system generated value. sysdate is a function which returns the current datetime; rownum is a pseudo-column that returns the row number in a result set.
The nomenclature dates from the earlier days of Oracle, before we had PL/SQL. It just means that we can use these functions in the projection of a SELECT statement, just like the columns of a table. Nowadays we can write our own functions and use them in SQL statements without blinking, and so the phrase "pseudo-column" is a tad confusing.
The feature which distinguishes a function from a pseudo-column is that the pseudo-column returns a different value for each row in the resultset whereas a function returns the same value (unless some column in the table is passed as a parameter to derive the value).
Dual is another venerable slice of Oracle history. It is a table which contains one row, and which the database knows contains one row. So the select statement you quote is just saying "give me the current datetime". It is functionally equivalent to
select sysdate
from emp
where rownum = 1
/
In PL/SQL the select from dual is nugatory. We can just code this:
l_date := sysdate;
One common use for DUAL used to be getting the next value of a sequence in a trigger. Since 11g we can do ...
:new.id := my_seq.nextval;
Under the covers this still executes select my_seq.nextval into :new.id from dual;
2. How does selecting from DUAL give the system time?
SQL has a number of built-in functions which don't need parentheses after them to invoke them. One such function in Oracle is SYSDATE.
Remember, if you have a table, a SELECT statement with no restriction condition (WHERE clause) normally returns one row of data for each row in the table. So, given a table:
CREATE TABLE Ex1(Dummy CHAR(10) NOT NULL);
INSERT INTO Ex1 VALUES('Abacus');
INSERT INTO Ex1 VALUES('Sedentary');
INSERT INTO Ex1 VALUES('Caucasus');
Running the SELECT statement:
SELECT Dummy FROM Ex1;
will return 3 rows. Now, suppose I write the statement as:
SELECT 'ABC', Dummy, SYSDATE FROM Ex1;
This will also return 3 rows:
ABC, Abacus, 2010-03-03
ABC, Sedentary, 2010-03-03
ABC, Caucasus, 2010-03-03
If I omit the Dummy column:
SELECT 'ABC', SYSDATE FROM Ex1;
I get:
ABC, 2010-03-03
ABC, 2010-03-03
ABC, 2010-03-03
And if I omit the string literal:
SELECT SYSDATE FROM Ex1;
I get:
2010-03-03
2010-03-03
2010-03-03
And I delete two rows and rerun the query, I get:
DELETE FROM Ex1 WHERE Dummy > 'B';
SELECT SYSDATE FROM Ex1;
I get:
2010-03-03
Because there's just the one row of data in the table Ex1.
Nominally, I could do:
UPDATE Ex1 SET Dummy = 'X';
RENAME TABLE Ex1 AS Dual;
Of course, you can't do that - I'm not sure whether Oracle supports a RENAME TABLE statement and it probably wouldn't let you rename your table so it could be confused with the built-in DUAL table. But conceptually, the table Ex1 with a single row in it is isomorphic with DUAL.
1. What is a Pseudo-Column?
Unless Oracle has a specific special meaning for the term, then a pseudo-column is a column that appears to be part of the table but that is not actually stored as data in the table. A classic example is a row number:
SELECT ROWNUM, * FROM SomeTable
The output appears to have a column ROWNUM (ROWID in Informix, with which I'm most familiar) but that is not directly stored in the DBMS. Different DBMS have other different pseudo-columns, for different purposes.
It is sometimes difficult to distinguish between a pseudo-column and a function.
A pseudo-column is an Oracle assigned value (pseudo-field) but not stored on disk.
Pseudocolumns are not actual columns in a table but they behave like columns.
For example, you can select values from a pseudocolumn. However, you cannot insert into, update, or delete from a pseudocolumn. Also note that pseudocolumns are allowed in SQL statements, but not in procedural statements.
NOTE:- pseudocolumns are allowed in SQL statements, but not in procedural statements.
SQL> SELECT sysdate, systimestamp FROM dual;
SYSDATE SYSTIMESTAMP
13-DEC-07 13-DEC-07 10.02.31.956842 AM +02:00
pseudo Columns : ROWID , ROWNUM , LEVEL