NOT IN in Hive QL - sql

I'm converting a SQL Server stored procedure to HiveQL.
How can I convert something like:
SELECT * FROM table1 WHERE id NOT IN (7,6,5,4,2,12)

NOT IN is now supported in Hive. See https://cwiki.apache.org/confluence/display/Hive/LanguageManual+UDF.

Try this:
SELECT * FROM table1 WHERE NOT array_contains(array(7,6,5,4,2,12), id)

According to the documentation it says you can use not in:
The negated forms can be written as follows:
from DomesticCat cat where cat.name not between 'A' and 'B'
from DomesticCat cat where cat.name not in ( 'Foo', 'Bar', 'Baz' )
Are you getting an error when you try your query in the question?
Please try based on the references as well.
Reference 1.
NOT IN Clause in HQL.

Related

How to use json column in the WHERE clause as a condition

The question is stated in the title and below is an example of the data
insert into table A values('a','b', {'key':'value'});
And I would like to be able to select this row based on the key-value pair using the WHERE clause. How can I do that?
Use JSON_VALUE:
SELECT t.*
FROM tableA t
WHERE JSON_VALUE(col3, '$.key') LIKE 'some_value'
This assumes that the column which contains the JSON value {'key':'value'} is called col3.
If you are using PostgreSQL then use below query
select * from table_name where column_name->>'key_name' = 'value_name';
Here is solution that's work for me:
column_name->'$.key'
Tested with mysql server 5.7.27

Postgresql 9.2 syntax issue

I am trying to execute this query using Postgresql 9.2
WITH udetail as (select(regexp_split_to_array('user#domain', E'\\#+')))
select * from udetail[1];
Buy it gives me a syntax error near where the start of '['. This same query is working fine under version 9.3. So I'm wonder if there's an alternative way of writing the query to get the same result.
I think you are looking for something like this:
WITH udetail(x) as (
select(regexp_split_to_array('user#domain', E'\\#+')))
select x[1] from udetail;
I don't think you can index a table expression like udetail in your case. It is the column of the table expression that is of array type. Hence, you can use an array subscript number on the column, not on the table itself.
Demo here
You should use an alias either as the query parameter:
with udetail(arr) as (
select regexp_split_to_array('user#domain', E'\\#+')
)
select arr[1] from udetail;
or as column alias:
with udetail as (
select regexp_split_to_array('user#domain', E'\\#+') as arr
)
select arr[1] from udetail;
You can also do it without aliases:
with udetail as (
select regexp_split_to_array('user#domain', E'\\#+')
)
select regexp_split_to_array[1] from udetail;

SELECT from nothing?

Is it possible to have a statement like
SELECT "Hello world"
WHERE 1 = 1
in SQL?
The main thing I want to know, is can I SELECT from nothing, ie not have a FROM clause.
It's not consistent across vendors - Oracle, MySQL, and DB2 support dual:
SELECT 'Hello world'
FROM DUAL
...while SQL Server, PostgreSQL, and SQLite don't require the FROM DUAL:
SELECT 'Hello world'
MySQL does support both ways.
Try this.
Single:
SELECT * FROM (VALUES ('Hello world')) t1 (col1) WHERE 1 = 1
Multi:
SELECT * FROM (VALUES ('Hello world'),('Hello world'),('Hello world')) t1 (col1) WHERE 1 = 1
more detail here : http://modern-sql.com/use-case/select-without-from
In Oracle:
SELECT 'Hello world' FROM dual
Dual equivalent in SQL Server:
SELECT 'Hello world'
Here is the most complete list of database support of dual from https://blog.jooq.org/tag/dual-table/:
In many other RDBMS, there is no need for dummy tables, as you can
issue statements like these:
SELECT 1;
SELECT 1 + 1;
SELECT SQRT(2);
These are the RDBMS, where the above is generally possible:
H2
MySQL
Ingres
Postgres
SQLite
SQL Server
Sybase ASE
In other RDBMS, dummy tables are required, like in Oracle. Hence,
you’ll need to write things like these:
SELECT 1 FROM DUAL;
SELECT 1 + 1 FROM DUAL;
SELECT SQRT(2) FROM DUAL;
These are the RDBMS and their respective dummy tables:
DB2: SYSIBM.DUAL
Derby: SYSIBM.SYSDUMMY1
H2: Optionally supports DUAL
HSQLDB: INFORMATION_SCHEMA.SYSTEM_USERS
MySQL: Optionally supports DUAL
Oracle: DUAL
Sybase SQL Anywhere: SYS.DUMMY
Ingres has no DUAL, but would actually need it as in Ingres you cannot
have a WHERE, GROUP BY or HAVING clause without a FROM clause.
In SQL Server type:
Select 'Your Text'
There is no need for the FROM or WHERE clause.
You can. I'm using the following lines in a StackExchange Data Explorer query:
SELECT
(SELECT COUNT(*) FROM VotesOnPosts WHERE VoteTypeName = 'UpMod' AND UserId = #UserID AND PostTypeId = 2) AS TotalUpVotes,
(SELECT COUNT(*) FROM Answers WHERE UserId = #UserID) AS TotalAnswers
The Data Exchange uses Transact-SQL (the SQL Server proprietary extensions to SQL).
You can try it yourself by running a query like:
SELECT 'Hello world'
There is another possibility - standalone VALUES():
VALUES ('Hello World');
Output:
column1
Hello World
It is useful when you need to specify multiple values in compact way:
VALUES (1, 'a'), (2, 'b'), (3, 'c');
Output:
column1 column2
1 a
2 b
3 c
DBFiddle Demo
This syntax is supported by SQLite/PostgreSQL/DB LUW/MariaDB 10.3.
In Firebird, you can do this:
select "Hello world" from RDB$DATABASE;
RDB$DATABASE is a special table that always has one row.
I think it is not possible. Theoretically: select performs two sorts of things:
narrow/broaden the set (set-theory);
mapping the result.
The first one can be seen as a horizontal diminishing opposed to the where-clause which can be seen as a vertical diminishing. On the other hand, a join can augment the set horizontally where a union can augment the set vertically.
augmentation diminishing
horizontal join/select select
vertical union where/inner-join
The second one is a mapping. A mapping, is more a converter. In SQL it takes some fields and returns zero or more fields. In the select, you can use some aggregate functions like, sum, avg etc. Or take all the columnvalues an convert them to string. In C# linq, we say that a select accepts an object of type T and returns an object of type U.
I think the confusion comes by the fact that you can do: select 'howdy' from <table_name>. This feature is the mapping, the converter part of the select. You are not printing something, but converting! In your example:
SELECT "
WHERE 1 = 1
you are converting nothing/null into "Hello world" and you narrow the set of nothing / no table into one row, which, imho make no sense at all.
You may notice that, if you don't constrain the number of columns, "Hello world" is printed for each available row in the table. I hope, you understand why by now. Your select takes nothing from the available columns and creates one column with the text: "Hello world".
So, my answer is NO. You can't just leave out the from-clause because the select always needs table-columns to perform on.
In Standard SQL, no. A WHERE clause implies a table expression.
From the SQL-92 spec:
7.6 "where clause"
Function
Specify a table derived by the
application of a "search condition" to
the result of the preceding "from
clause".
In turn:
7.4 "from clause"
Function
Specify a table derived from one or more named tables.
A Standard way of doing it (i.e. should work on any SQL product):
SELECT DISTINCT 'Hello world' AS new_value
FROM AnyTableWithOneOrMoreRows
WHERE 1 = 1;
...assuming you want to change the WHERE clause to something more meaningful, otherwise it can be omitted.
For ClickHouse, the nothing is system.one
SELECT 1 FROM system.one
I know this is an old question but the best workaround for your question is using a dummy subquery:
SELECT 'Hello World'
FROM (SELECT name='Nothing') n
WHERE 1=1
This way you can have WHERE and any clause (like Joins or Apply, etc.) after the select statement since the dummy subquery forces the use of the FROM clause without changing the result.
For DB2:
`VALUES('Hello world')`
You can do multiple "rows" as well:
`VALUES('Hello world'),('Goodbye world');`
You can even use them in joins as long as the types match:
VALUES(1,'Hello world')
UNION ALL
VALUES(2,'Goodbye world');
I'm using firebird
First of all, create a one column table named "NoTable" like this
CREATE TABLE NOTABLE
(
NOCOLUMN INTEGER
);
INSERT INTO NOTABLE VALUES (0); -- You can put any value
now you can write this
select 'hello world' as name
from notable
you can add any column you want to be shown

Select query in SQL

I have a very curious question.
We have query to select records from table based on some condition. In general the syntax for the query is as below
SELECT * FROM TABLENAME WHERE COLUMNNAME='VALUE';
Now the question is that will this query will work if we interchange the position of COLUMNNAME and 'VALUE'.
Yes, it will. =)
Why did you not just try?
Yes. The following will work:
SELECT * FROM TABLENAME WHERE 'VALUE' = COLUMNNAME;
In fact, in Oracle at least, you can do some twisted but somewhat useful things like:
select *
from tablename
where 'VALUE' in (field1, field2, field3)
You mean
SELECT * FROM TABLENAME WHERE 'VALUE' = COLUMNNAME;
I tested it, it works on MSSQL Servver 2008
SELECT * FROM TABLENAME WHERE 'VALUE' = COLUMNNAME;
if write something like this.. it'll work for sure..

FROM clause necessary in every SELECT statement

is the FROM clause necessary in every SELECT statement?Thanks..
Not really - you can use SELECT to initialize a variable.
Examples from here:
mysql> SELECT 1 + 1;
-> 2
Not in MySQL, no. You could do this:
SELECT 1 + 1;
It will be in some DBMSs though - Oracle for example would require you to do:
SELECT 1 + 1 FROM DUAL;
No. you can very easily do
SELECT 1+1
(EDIT: Missed the the MYSQL tab.)
This depends on the database.
In Oracle, IIRC, the from is required. But Oracle has a table DUAL which always returns one row for cases where all the work is being done in the SELECT clause.
On the other hand, SQL Server does not require the FROM, to return the value of a variable just select it:
SELECT #myVar
As mentioned by ocedecio FROM is not required in every statement.
For example I tend to use the following syntax to initialise a table with data
insert into status(code, description)
select 'O', 'Open'
union all select 'C', 'Closed'
union all select 'P', 'Parked'
etc..
EDIT (following comments by gamecat)
The example above demonstrates when SELECT without FROM may have a practical use.
You can of course just call:
select 'O', 'Open'
union all select 'C', 'Closed'
union all select 'P', 'Parked'
Basically in SQL server 2005 FROM keyword is not required for Scalar value functions and system functions but it mandatory for table valued functions.
Scalar valued functions can executable like below syntax
Select functionname(arguments)
Table valued functions can executable like below syntax
Select * from functionname(arguments)
else
Select col1,col2 from functionname(argument1,argument2)
Actually, both "SELECT 1" and "SELECT 1 FROM DUAL" work in latest versions of MySQL.
Interesting enough, "SELECT 1 WHERE 1 = 1" requires a FROM clause: "SELECT 1 FROM DUAL WHERE 1 = 1" is fine. In other platforms, like PostgreSQL, "SELECT 1 WHERE 1 = 1" works fine.
Another oddity: "SELECT 1 FROM DUAL GROUP BY 1 HAVING 1=1" works in MySQL 5.7, but fails in MySQL 5.5.
Summary of the required/optional FROM clause in different platforms:
MySQL, MariaDB, Amazon Aurora: optional or use "FROM dual".
Oracle: use "FROM dual".
IBM DB2: use "FROM sysibm.sysdummy1".
Informix: use "FROM systables WHERE tabid=1"
Firebird, InterBase: use "FROM rdb$database".
Microsoft Access: required, but no dummy table. Try using "FROM (SELECT COUNT(*) FROM first_table_found WHERE 1=0) AS dual".
SQL Server, SQL Azure, SQL Server CE, Sybase ASE, SQL Anywhere, Ingres, PostgreSQL, Redshift, SQLite: optional.