I have a function that returns the format of formula.some part of it----
if(CHARINDEX(#fieldname,#formula)<>0)
Begin
declare #previouschar char = SUBSTRING(#formula, CHARINDEX(#fieldname, #formula)-1, 1),
#nextchar char = SUBSTRING(#formula, CHARINDEX(#fieldname ,#formula)+len(#fieldname), 1)
if(#previouschar in('[',']','(',')','{','}','+','-','/','*')
and #nextchar in ('[',']','(',')','{','}','+','-','/','*'))
Begin
set #calFormula= replace(#calFormula,#fieldname,' case when FLD'+Convert(varchar,#flid)+' is null OR FLD'+Convert(varchar,#flid)+'='''' then 0.0 else Convert(decimal(18,'+ Convert(varchar,#decimalPlc) +'),FLD'+Convert(varchar,#flid)+' ) end ')
End
end
set #cnt1=#cnt1+1
End
set #calFormula= replace(#calFormula,'[','')
set #calFormula= replace(#calFormula,']','')
return #calFormula
I want to implement ISERROR method of DAX in Sql Server Relational Database that would check if any divisor entered is zero then it assigns NULL in calculated formula.How to work for this?Can there be some alternate method like ISERROR in SQL?
Sure.
IsError(1/0) will return true (because there is an error)
IsError(1/1) will return false (no error).
Technet
Related
I have an Oracle function that needs to be converted to SQL-Server function
This is the Oracle Function:
FUNCTION check_education(in_crs_code IN VARCHAR2)
RETURN BOOLEAN IS
v_bool BOOLEAN := FALSE;
v_dummy VARCHAR2(1);
CURSOR find_education IS
SELECT 'x'
FROM KU_LIBRARY_EDUCATION_EXTLOAN
WHERE UPPER(course_code) = UPPER(in_crs_code) AND in_use = 'Y';
BEGIN
OPEN find_education;
FETCH find_education INTO v_dummy;
IF find_education%FOUND THEN
v_bool := TRUE;
ELSE
v_bool := FALSE;
END IF;
CLOSE find_education;
RETURN (v_bool);
END check_education;
This is what I have written in SQL-Server to replicate Oracle function:
CREATE FUNCTION [dbo].[check_education](#in_crs_code VARCHAR(4000))
RETURNS BIT AS
BEGIN
DECLARE #v_bool BIT = 0;
DECLARE #v_dummy VARCHAR(1);
DECLARE find_education CURSOR LOCAL FOR
SELECT 'x'
FROM [dbo].[KU_LIBRARY_EDUCATION_EXTLOAN]
WHERE UPPER(course_code) = UPPER(#in_crs_code)
AND in_use = 'Y';
OPEN find_education;
FETCH find_education INTO #v_dummy;
IF ##CURSOR_ROWS >1 BEGIN
SET #v_bool = 1;
END
ELSE BEGIN
SET #v_bool = 0;
END
CLOSE find_education;
DEALLOCATE find_education;
RETURN (#v_bool);
END;
I would expect the SQL server function to return 1 if the cursor returns 'x' but i'm getting 0. Anu help will be appreciated.
I would suggest using an inline table valued function instead of a scalar function. To make sure this is an inline table valued function it MUST be a single select statement. This means there can't be loops and other stuff. Fortunately this query does not actually need any loops. A simple count will return the number of rows. And any value other than 0 when converted to a bit will always be 1.
CREATE FUNCTION [dbo].[check_education]
(
#in_crs_code VARCHAR(4000)
) RETURNS table as return
SELECT CourseExists = convert(bit, count(*))
FROM [dbo].[KU_LIBRARY_EDUCATION_EXTLOAN]
WHERE UPPER(course_code) = UPPER(#in_crs_code)
AND in_use = 'Y';
This is a mere EXISTS thing, so we could try
CREATE FUNCTION [dbo].[check_education](#in_crs_code VARCHAR(4000)) RETURNS BIT AS
BEGIN
RETURN EXISTS ( <query> )
END;
But as far as I know, SQL Server doesn't accept this (though I cannot say why not - maybe it's because of their lack of a real boolean; Oracle doesn't accept it, because EXISTS is no keyword in their PL/SQL programming language).
So we'd use IF/ THEN/ ELSE:
CREATE FUNCTION [dbo].[check_education](#in_crs_code VARCHAR(4000)) RETURNS BIT AS
BEGIN
IF EXISTS
(
SELECT 'x'
FROM ku_library_education_extloan
WHERE UPPER(course_code) = UPPER(in_crs_code) AND in_use = 'Y'
)
RETURN 1
ELSE
RETURN 0
END
END;
There may be errors, because I've never coded a stored procedure in T-SQL, but anyway, you get the idea.
I have created a stored procedure for deleting record. In this stored procedure I am first checking for the usage of data which I am going to delete. If it is being used, then the stored procedure will return -2 otherwise it deletes the record.
But the problem is that even the record exists its return -1 instead of -2. I have also set the NOCOUNT OFF but don't know where is the problem.
I know this question is already answered by setting NOCOUNT OFF but its not working for me
ALTER PROCEDURE [dbo].[spDeletePIDNumber]
#Id int
AS
BEGIN
SET NOCOUNT OFF;
-- Insert statements for procedure here
if(exists(select * from tblBills where PID = #Id))
begin
return -2
end
else
begin
Delete from HelperPIDNumber
where Id = #Id
end
END
public int DeletePIDNumber(int Id)
{
try
{
int result = 0;
using (SqlConnection conn = new SqlConnection(Properties.Settings.Default.connection))
{
var cmd = new SqlCommand("spDeletePIDNumber", conn);
cmd.CommandType = System.Data.CommandType.StoredProcedure;
cmd.Parameters.AddWithValue("#Id", Id);
conn.Open();
result = cmd.ExecuteNonQuery();
}
return result;
}
catch
{
throw;
}
}
From the ExecuteNonQuery documentation:
Executes a Transact-SQL statement against the connection and returns the number of rows affected.
Having SET NOCOUNT ON; in your procedure explicitely tells to SQL Server not to return a row count. In that case the return of the ExecuteNonQuery function is -1.
Also if the procedure does not affect any rows, it will not return a row count either even if NOCOUNT is OFF. In that case the return will also be -1.
What you appear to want to do is get the return value of the stored procedure. You will not get that from the result of ExecuteNonQuery. Please refer to this question on StackOverflow: Getting return value from stored procedure in ADO.NET
Generally ExecuteNonQuery will return number of affected records. It will return -1 in two cases:
When SET NOCOUNT ON has been set. From your code, its clear, you have SET NOCOUNT OFF and so this is not an issue at your case.
If number of affected rows is nothing, it will return -1. In your case, it looks like you are checking the data exists from one table tblBills and delete from another table HelperPIDNumber. So there is more chance there will be no matching record and nothing deleted.
Please check the point # 2 above.
if( exists(select * from tblBills where PID = #Id))
begin
return -2
end
else
begin
Delete from HelperPIDNumber where Id = #Id
end
use cmd.ExecuteScalar() instead of cmd.ExecuteNonQuery() ascmd.ExecuteNonQuery() return only the number of affected rows and not the value you are selecting.
I came across the following solution but it does not work on Sybase
SELECT CONVERT(varchar, CAST(987654321 AS money), 1)
I have read the Convert Sybase information but still i receive the same number without the commas.
Have you tried giving a varchar (20) for example instead ? something like :
SELECT CONVERT(varchar(20), CAST(987654321 AS money), 1)
In SqlAnywhere money datatype is a domain, implemented as NUMERIC(19,4).
in CAST function , If you do not indicate a length for character string types, the database server chooses an appropriate length. If neither precision nor scale is specified for a DECIMAL conversion, the database server selects appropriate values.
So maybe this is what's causing the issue, what do you get as output ? do you get 987654321.00 , or just 987654321 ?
Update:
My last suggestion would be using insertstr() function and loop through the char value of your number to insert comma every 3 digits .. this is not the cleanest/easiest way but apparently SQLAnywhere deal with money datatype as normal NUMERIC datatype ...
insertstr() documentation is here.
I would give you a code sample but I don't have SQLAnywhere installed to test it ...
Here is the SP i created based on F Karam suggestion.
CREATE FUNCTION "DBA"."formattednumber"( in #number numeric)
returns char(60)
begin
declare #returnnumber char(60);
declare #workingnumber char(60);
declare #n_ind char(1);
declare #decimalnumber char(10);
declare #tempnumber char(60);
declare #decimalpos integer;
if isnull(#number,'') = '' then
return null
end if;
if #number < 0 then set #n_ind = 'Y'
else set #n_ind = 'N'
end if;
set #workingnumber = convert(char(60),ABS(#number));
set #decimalpos = patindex('%.%',#workingnumber);
if #decimalpos > 0 then
set #decimalnumber = substr(#workingnumber,#decimalpos);
set #decimalnumber = "left"(#decimalnumber,3+1);
set #workingnumber = "left"(#workingnumber,#decimalpos-1)
end if end if;
set #returnnumber = '';
while length(#workingnumber) > 3 loop
set #tempnumber = "right"(#workingnumber,3);
set #returnnumber = insertstr(0,#returnnumber,#tempnumber);
set #workingnumber = "left"(#workingnumber,length(#workingnumber)-3);
if length(#workingnumber) > 0 then
set #returnnumber = insertstr(0,#returnnumber,',')
end if
end loop;
if length(#workingnumber) > 0 then
set #returnnumber = insertstr(0,#returnnumber,#workingnumber)
end if;
if length(#decimalnumber) > 0 then
set #returnnumber = #returnnumber+#decimalnumber
end if;
if #n_ind = 'Y' then set #returnnumber = '-' || #returnnumber
end if;
return(#returnnumber)
end;
You need to distinguish between server-side and client-side formatting. When you use the 'isql' client for example (the TDS client), then the result will be this:
1> select convert(money, 9876543210)
2> go
9876543210
------------------------
9,876,543,210.00
(1 row affected)
But this is purely because the client application happens to format 'money' values this way. Also, this is actually not specific for SQLA, since isql is originally the client tool for ASE (a different Sybase database).
When you run the same conversion at the SQLA server (i.e. as part of an expression in a SQL statement), those commas will not be there since SQLA doesn't have such a built-in formatting style.
If you want this, you should write a SQL function that formats the number as you desire.
I have a stored procedure inserts a row, and some conditions returns result set or single error code but when I use dapper return always same return class. so I couldn't understand If code gives me error or message rather than successful result set.
public static List<Result> Results(int Id)
{
using (IDbConnection connection = BL.DataProvider.OpenConnection())
{
return connection.Query<Result>("SearchResultGet", new { Id = Id }, commandType: CommandType.StoredProcedure).ToList();
}
}
ALTER PROCEDURE SearchResultGet
#Id int
AS
IF(id != 0)
SELECT * FROM XX WHERE Id = Id
ELSE
SELECT -1
codes are just sample, doesn't have any meaning.
There is no ORM/micro-ORM API that is going to like this; having a select -1 for one set of cases is just ... not pleasant. Options:
change the sproc to not do that - just run the regular select that returns zero rows
add the logic to the Results method instead (or in addition to) the sproc - i.e. check whether Id is zero in the C#
use a return -1 rather than a select -1 (although note that dapper doesn't make it trivial to capture return values)
use a sql error (raiserror)
I have an SP with some condition like this
IF NOT EXISTS (Select * from bom_steel where fpart = #fpart)
BEGIN
INSERT INTO bom_steel
VALUES (#fPart,#fL,#fH,#fW,#fDesc)
END
ELSE if(Select * from Employee where Empid = #empid)
BEGIN
Return ‘1’
END
Else
Begin
UPDATE bom_steel
SET fl=#fl, fh=#fH, fW=#fW
where Empid =# empid
end
when this condition passes , I am returning an value as 1
ELSE if(Select * from Employee where Empid = #empid)
BEGIN // here i will to be doing any operation(DML) .so i want to just return an value as '1'
Return ‘1’
END
In my code behind
Here cmd is SqlCommand
Int intcount= cmd.ExecuteNonQuery();
Here in this condition it always retuens an value as -1;
Even I am setting an return value as ‘1’it is still returingf an value as -1
can any one tell me what should i do in order to return an value as 1 from there
any help would be great
thanks
Try doing
Int intcount= cmd.ExecuteScalar();
instead of
Int intcount= cmd.ExecuteNonQuery();
ExecuteNonQuery() only returns the number of rows affected.
Also, additionally, remove the single quotes in the return value as Andrew indicated below or change the type of intCount to string instead.
You are trying to return a character value, not an int. Try removing the single quotes.
Also what InSane said; ExecuteNonQuery() returns the number of rows affected. Though that makes me wonder about your example; why would that return -1?