Showing posts with label howcan. Show all posts
Showing posts with label howcan. Show all posts

Thursday, March 8, 2012

Conditional JOIN

Hi,

I am trying to change an SP from dynamic SQL to proper SQL but I can't
figure a way to conditionally add extra parts to the statement. How
can I do the equivalent of the following?

DECLARE @.arg NVARCHAR(10)

SELECT a.i, a.x
FROM aTable a
IF LEN(@.arg)
BEGIN
INNER JOIN bTable b ON a.[id] = b.[id]
END

Conditionally adding the INNER JOIN is very easy when building up a SQL
string but I can't see how to do it in pure SQL?

Thanks.What do you intend by a conditional join? The purpose of a join is
usually to bring back some extra columns from additional tables. Static
queries also have static metadata (in other words always the same set
of columns are returned every time) so a "conditional" join such as you
have posted is really just a selection:

SELECT a.i, a.x
FROM aTable AS a
WHERE EXISTS
(SELECT *
FROM bTable AS b
WHERE b.id = a.id)
OR @.arg = ''

(I'm assuming ID is unique in B otherwise your original query might
return duplicate rows).

In general you can use OR to implement optional criteria but this often
leads to sub-optimal query plans. You should consider using IF
statements to choose from a set of possible queries or just break up
the different queries into separate SPs to be called independently.
Either approach is usually preferable to dynamic SQL.

--
David Portas
SQL Server MVP
--|||I possibly gave a less than clear example. Insert an additional join
on aTable:

SELECT a.i, a.x
FROM aTable a
INNER JOIN bTable b on a.[id] = b.[id]
IF (LEN(@.arg) > 0)
BEGIN
INNER JOIN cTable c ON a.[id] = c.[id]
END

The condition is that if the parameter @.arg is of length 0 then I do
not want to join to cTable but if it is greater than 0 then I do. It's
essentially a switch to impose additional restrictions upon the
recordset being returned. I am not changing the structure of what is
being selected, just _conditionally_ adding an extra filter on the
data.

Thanks.|||SELECT a.i, a.x
FROM aTable a
INNER JOIN bTable b
ON a.[id] = b.[id]
WHERE EXISTS
(SELECT *
FROM cTable c
WHERE c.[id] = a.[id])
OR @.arg = ''

Again, assuming ID is unique in C this is equivalent to an INNER JOIN.

--
David Portas
SQL Server MVP
--|||(chandy@.totalise.co.uk) writes:
> I possibly gave a less than clear example. Insert an additional join
> on aTable:
> SELECT a.i, a.x
> FROM aTable a
> INNER JOIN bTable b on a.[id] = b.[id]
> IF (LEN(@.arg) > 0)
> BEGIN
> INNER JOIN cTable c ON a.[id] = c.[id]
> END
> The condition is that if the parameter @.arg is of length 0 then I do
> not want to join to cTable but if it is greater than 0 then I do. It's
> essentially a switch to impose additional restrictions upon the
> recordset being returned. I am not changing the structure of what is
> being selected, just _conditionally_ adding an extra filter on the
> data.

And that is exactly what David's query achieved. He hinted that his query
might not get a good query plan, but in fact

SELECT a.i, a.x
FROM aTable AS a
WHERE EXISTS
(SELECT *
FROM bTable AS b
WHERE b.id = a.id)
OR @.arg = ''

should perform very well when @.arg is ''. SQL Server will understand
that it does have to access bTable at all. It will appear in the plan,
but a so-called startup expression prevents it from being accessed when
there is no need to. (Interested readers can find more details on
this in http://www.sommarskog.se/dyn-search...mplexconditions.)

--
Erland Sommarskog, SQL Server MVP, esquel@.sommarskog.se

Books Online for SQL Server SP3 at
http://www.microsoft.com/sql/techin.../2000/books.asp|||Ahh, I get it now, hadn't fully comprehended what the WHERE EXISTS was
doing. That seems to work nicely.

Thanks!

Sunday, February 12, 2012

concatenation

I am trying to concatenate a long string together ad it keeps truncating how
can I extend the length that is allowed to truncate?
TIAHow do you it is being truncated?
Can you post the code?
AMB
"JMNUSS" wrote:

> I am trying to concatenate a long string together ad it keeps truncating h
ow
> can I extend the length that is allowed to truncate?
> TIA|||maybe truncated wasn't the correct term. The string is being cut off at the
end...
What I want to see is something like "this<>is<> a<>long<> string"
What is get is "this<> is<> a<> lon"
and that's it
"Alejandro Mesa" wrote:
> How do you it is being truncated?
> Can you post the code?
>
> AMB
> "JMNUSS" wrote:
>|||How long a string?
Where are you doing the concatenation?
Show us some code.
"JMNUSS" <JMNUSS@.discussions.microsoft.com> wrote in message
news:061DB1FF-1529-45B7-B51E-8627A6162936@.microsoft.com...
> I am trying to concatenate a long string together ad it keeps truncating
how
> can I extend the length that is allowed to truncate?
> TIA|||No, you can not do that. You can insert the result of the sp into a table an
d
then process the table, or you can rewrite the sp as a table-valued user
defined function, or you can call the sp using rowset function.
Example:
use northwind
go
create table #t (
Shippeddate datetime,
OrderID int,
Subtotal money,
col_Year int
)
insert into #t
execute dbo.[Sales by Year] '19960101', '19961231'
select
*
from
#t
where
Subtotal between 1200.00 and 1500.00
drop table #t
go
AMB
"JMNUSS" wrote:

> I am trying to concatenate a long string together ad it keeps truncating h
ow
> can I extend the length that is allowed to truncate?
> TIA|||Are you viewing this in Query Analyser?
If so: Tools/Options/Results and change the "Maximum characters per column"
"JMNUSS" <JMNUSS@.discussions.microsoft.com> wrote in message
news:B1036631-B165-4251-AF5B-A6C3777C0705@.microsoft.com...
> maybe truncated wasn't the correct term. The string is being cut off at
the
> end...
> What I want to see is something like "this<>is<> a<>long<> string"
> What is get is "this<> is<> a<> lon"
> and that's it
> "Alejandro Mesa" wrote:
>
truncating how|||Sorry.
AMB
"Alejandro Mesa" wrote:
> No, you can not do that. You can insert the result of the sp into a table
and
> then process the table, or you can rewrite the sp as a table-valued user
> defined function, or you can call the sp using rowset function.
> Example:
> use northwind
> go
> create table #t (
> Shippeddate datetime,
> OrderID int,
> Subtotal money,
> col_Year int
> )
> insert into #t
> execute dbo.[Sales by Year] '19960101', '19961231'
> select
> *
> from
> #t
> where
> Subtotal between 1200.00 and 1500.00
> drop table #t
> go
>
> AMB
>
> "JMNUSS" wrote:
>|||> What is get is "this<> is<> a<> lon"
Where do you get this, in your client app?
If you are using SQL Query Analyzer and the result is being truncated, go to
tools - Options - Results and change "Maximum characters per column:" (max
number is 8192).
AMB
"JMNUSS" wrote:
> maybe truncated wasn't the correct term. The string is being cut off at t
he
> end...
> What I want to see is something like "this<>is<> a<>long<> string"
> What is get is "this<> is<> a<> lon"
> and that's it
> "Alejandro Mesa" wrote:
>|||Heh Alejandro, get in the right thread...
"Alejandro Mesa" <AlejandroMesa@.discussions.microsoft.com> wrote in message
news:58BD3B7D-A23E-44BC-9008-4276A8B7DE58@.microsoft.com...
> No, you can not do that. You can insert the result of the sp into a table
and
> then process the table, or you can rewrite the sp as a table-valued user
> defined function, or you can call the sp using rowset function.
> Example:
> use northwind
> go
> create table #t (
> Shippeddate datetime,
> OrderID int,
> Subtotal money,
> col_Year int
> )
> insert into #t
> execute dbo.[Sales by Year] '19960101', '19961231'
> select
> *
> from
> #t
> where
> Subtotal between 1200.00 and 1500.00
> drop table #t
> go
>
> AMB
>
> "JMNUSS" wrote:
>
how