How to show only real number with SQL Select ?
As example the data in table appear like :
Price
100000
10.0022
99980
0.0005
1.5
25000
0
20.5
The price data type is number.
I try SQL query like this but fail :
SELECT price FROM price_table WHERE price LIKE '%.%';
The query return error :
ERROR: operator does not exist: numeric ~~ unknown
LIKE is for strings, not for numbers. If you want to find those that do have decimal digits, compare them to their integer value:
select *
from price_table
where price::int <> price;
To be able to use LIKE you need to first convert the number to a string:
select *
from price_table
where price::text like '%.%';
Related
Hi I'm trying to create a simple query to find the products with more than 5000mAh since this a type VARCHAR2 I'm unable to set the condition with just numbers. I have tried using TO_NUMBER to convert string to number but I get.
ORA-01722: invalid number
Here is the query
SELECT Product.product_name, Product.battery FROM Product WHERE battery >= TO_NUMBER('5000');
INSERT INTO Product (product_id,product_categ_type_id,product_name,price,stock_qty,screen_size,cpu,ram, battery,colour)
VALUES((110,2,'Samsung 9 Plus',267,191,'10.1','Octa 1.3GHz','6GB', '3500mAh', 'Blue')
INSERT INTO Product (product_id,product_categ_type_id,product_name,price,stock_qty,screen_size,cpu,ram, battery,colour)
VALUES((116,2,'Huawei P50Pro',393,138,'6.0','Octa 2.5GHz','16GB', '6400mAh', 'Black')
INSERT INTO Product (product_id,product_categ_type_id,product_name,price,stock_qty,screen_size,cpu,ram, battery,colour)
VALUES((194,3,'Samsung Galaxy Tab',398,138,'10.10','Octa 1.6GHz','2GB', '7300mAh', 'Black')
You need a REGEXP_SUBSTR for this instead of TO_NUMBER only -
SELECT Product.product_name, Product.battery
FROM Product
WHERE REGEXP_SUBSTR(battery, '\d+') >= 5000;
Demo.
When you do:
SELECT Product.product_name, Product.battery FROM Product WHERE battery >= TO_NUMBER('5000');
... you are converting the wrong side of the comparison, and forcing an implicit conversion of your column value to a number; it should be:
SELECT Product.product_name, Product.battery FROM Product WHERE TO_NUMBER(battery) >=5000;
... but that will still get the same error "ORA-01722: invalid number" because you have unrecognised non-digit characters.
Rather than using a (possibly expensive and slow) regular expression to extract the digits, if the battery is always quoted in 'mAh' exactly as you've shown then you could treat that as if was was a currency:
SELECT Product.product_name, Product.battery
FROM Product
WHERE TO_NUMBER(battery, '999999L', 'nls_currency=mAh') >=5000;
PRODUCT_NAME
BATTERY
Huawei P50Pro
6400mAh
Samsung Galaxy Tab
7300mAh
fiddle
A very simple query which work
select avg(price) from cars where type = 'electric';
the result is
1
---------------------------------
45000,00000000000
I want to remove the ,00000000000 to obtain
1
---------------------------------
45000
I have tried cast and round but without success.
I'm on Db2
This nice ltrim works fine for all type of cars
select replace(ltrim(replace(price,'0',' ')),' ','0') from cars;
but using with avg return the string with the 00000
select replace(ltrim(replace(avg(price),'0',' ')),' ','0') from cars where type = 'electric';
the result is..
45000.00000000000
:(
Only the , is changed.
casting this value should just work:
select cast(avg(price) as int) as avg_int
from cars
where type = 'electric';
Casting as an integer as suggested by another answer will work.
However, keep in mind that
you'll be truncating any decimal values.
you're converting from one type to another.
You can resolve #1 by casting after ROUND()
select int(round(avg(price),0)) as avg_int
from cars
where type = 'electric'
You can resolve #2 by using DECIMAL() or ZONED() with zero for scale depending on the original column type.
select dec(avg(price),10,0) as avg_dec
from cars
where type = 'electric'
And of course ROUND() could be used with DECIMAL() or ZONED() also...
I query two values from a table. I want to use the second value to set the decimal scale of the first value. Would anyone know how to set this using to_char? I was looking at the formats and I'm not sure how to make the int I'm receiving into the format I need. Here is my code:
with tmp as (select num, scale
from tl)
select fun, num
from fun_table f, tmp
where f.fun = tmp.scale;
EDIT:
if I receive num as 5.87 and scale as 3 I want the result to be 5.870
num: 7.00 scale: 1 expected output: 7.0
num: 7 scale: 4 expected output: 7.0000
Something like this?
SELECT TO_CHAR(num, CONCAT('99D',RPAD('9',scale,'9'))) FROM tl
or, if scale can be 0 and you don't want to show the decimal separator in such cases,
SELECT TO_CHAR(num, CONCAT('99',RPAD('D',scale+1,'9'))) FROM tl
Tested on Oracle Database 11g.
select round(fun,scale) from fun_table f, tmp where f.fun = tmp.scale;
Maybe this is what you're looking for? Depending on the logic you want you may want to replace round function with floor or ceil.
I am trying to take an average of a column in my database. The column is AMOUNT and it is stored as NVARCHAR(300),null.
When I try to convert it to a numeric value I get the following error:
Msg 8114, Level 16, State 5, Line 1
Error converting datatype NVARCHAR to NUMBER
Here is what I have right now.
SELECT AVG(CAST(Reimbursement AS DECIMAL(18,2)) AS Amount
FROM Database
WHERE ISNUMERIC(Reimbursement) = 1
AND Reimbursement IS NOT NULL
You would think that your code would work. However, SQL Server does not guarantee that the WHERE clause filters the database before the conversion for the SELECT takes place. In my opinion this is a bug. In Microsoft's opinion, this is an optimization feature.
Hence, your WHERE is not guaranteed to work. Even using a CTE doesn't fix the problem.
The best solution is TRY_CONVERT() available in SQL Server 2012+:
SELECT AVG(TRY_CONVERT(DECIMAL(18,2), Reimbursement)) AS Amount
FROM Database
WHERE ISNUMERIC(Reimbursement) = 1 AND Reimbursement IS NOT NULL;
In earlier versions, you can use CASE. The CASE does guarantee the sequential ordering of the clauses, so:
SELECT AVG(CASE WHEN ISNUMERIC(Reimbursement) = 1 AND Reimbursement IS NOT NULL
THEN CONVERT(DECIMAL(18,2), Reimbursement))
END)
FROM Database;
Because AVG() ignores NULL values, the WHERE is not necessary, but you can include it if you like.
Finally, you could simplify your code by using a computed column:
alter database add Reimbursement_Value as
(CASE WHEN ISNUMERIC(Reimbursement) = 1 AND Reimbursement IS NOT NULL
THEN CONVERT(DECIMAL(18,2), Reimbursement))
END);
Then you could write the code as:
select avg(Reimbursement_Value)
from database
where Reimbursement_Value is not null;
Quote from MSDN...
ISNUMERIC returns 1 for some characters that are not numbers, such as plus (+), minus (-), and valid currency symbols such as the dollar sign ($). For a complete list of currency symbols, see money and smallmoney
select isnumeric('+')---1
select isnumeric('$')---1
so try to add to avoid non numeric numbers messing with your ouput..
WHERE Reimbursement NOT LIKE '%[^0-9]%'
If you are on SQLServer 2012,you could try using TRY_Convert which outputs null for conversion failures..
SELECT AVG(try_convert( DECIMAL(18,2),Reimbursement))
from
table
I am guessing that since it is Nvarchar you are going to find some values in there with a '$','.', or a (,). I would run a query likt this:
SELECT Amount
FROM database
WHERE Amount LIKE '%$%' OR
Amount LIKE '%.%' OR
Amount LIKE '%,%'
See what you get and my guess you will get some rows returned and then update those rows and try it again.
Currently your query would pull all numbers that are not all numeric which is a reason why it is failing too. Instead try running this:
SELECT AVG(CAST(Reimbursement AS DECIMAL(18,2)) AS Amount
FROM Database
--Changed ISNUMERIC() = to 0 for true so it will only pull numeric numbers.
WHERE ISNUMERIC(Reimbursement) = 0 and Reimbursement IS NOT NULL
I am using the following query.
select * from wp_rg_lead_detail where lead_id=5063 and field_number=cast(1.6 as decimal).
but it returns the field number 2 result instead of 1.6
Please let me know how can I do it?
Here:
select * from wp_rg_lead_detail where lead_id=5063 and field_number=cast(1.6 as decimal(2, 1))
You must specify number of digits in your decimal when casting, an number of digits after coma (I set them to 2 digits decimal with 1 after coma). You can easily test such casting by simply writing query:
SELECT Cast( 1.6 as decimal(2,1))
this will produce you effect of your casting. If you don't include (2,1) part, it will be automatically rounded to 2.