Showing posts with label condition. Show all posts
Showing posts with label condition. Show all posts

Sunday, March 11, 2012

Change condition if the first doesn't exists

Have two tables:
code:

CREATE TABLE [Table1]
(
[Id] [int] IDENTITY (1, 1) NOT FOR REPLICATION NOT NULL ,
[Number] [varchar] (50) NOT NULL ,
[TimeStamp] [smalldatetime] NOT NULL CONSTRAINT [DF_Table1_TimeStamp]
DEFAULT (getdate()),
CONSTRAINT [PK_Table1] PRIMARY KEY CLUSTERED
(
[Id]
) ON [PRIMARY]
) ON [PRIMARY]
GO
CREATE TABLE [Table2]
(
[Id] [int] IDENTITY (1, 1) NOT FOR REPLICATION NOT NULL ,
[Table1Id] [int] NOT NULL ,
[LingoId] [int] NOT NULL ,
[Header] [nvarchar] (150) NOT NULL ,
[Description] [ntext] NOT NULL ,
CONSTRAINT [PK_Table2] PRIMARY KEY CLUSTERED
(
[Id]
) ON [PRIMARY] ,
CONSTRAINT [FK_Table2_Table1] FOREIGN KEY
(
[Table1Id]
) REFERENCES [Table1] (
[Id]
)
) ON [PRIMARY] TEXTIMAGE_ON [PRIMARY]
GO


What I would like is that if LingoId = 2 in the query below doesn't exists
than it should fall thru and use the values where LingoId = 1. LingoId = 1
always exists for each Table2.Id. Is this doable?
code:

SELECT
dbo.Table1.Id,
dbo.Table1.Number,
dbo.Table1.[TimeStamp],
dbo.Table2.Header,
dbo.Table2.Description
FROM
dbo.Table1
LEFT OUTER JOIN
dbo.Table2 ON dbo.Table1.Id = dbo.Table2.Table1Id
WHERE
(dbo.Table2.LingoId = 2) --Something should happen here I quess.

SELECT
dbo.Table1.Id,
dbo.Table1.Number,
dbo.Table1.[TimeStamp],
(CASE WHEN T2_2.Existing IS NOT NULL THEN T2_2.Header ELSE
T2_1.Header END) as Header,
(CASE WHEN T2_2.Existing IS NOT NULL THEN T2_2.Description ELSE
T2_1.Description END) as Description
FROM
dbo.Table1
LEFT OUTER JOIN
(SELECT dbo.Table2.Header, dbo.Table2.Description, 'Exists'
Existing FROM Table2 Where Lingold = 2) T2_2
ON dbo.Table1.Id = T2_2.Table1Id
LEFT OUTER JOIN
(SELECT dbo.Table2.Header, dbo.Table2.Description, 'Exists'
Existing FROM Table2 Where Lingold = 1) T2_1
ON dbo.Table1.Id = T2_1.Table1Id
HTH, Jens Suessmeyer.|||Got an answer elsewhere that did the trick.
"Senna" wrote:

>
Have two tables:
>
>
code:

>
CREATE TABLE [Table1]
>
(
>
[Id] [int] IDENTITY (1, 1) NOT FOR REPLICATION NOT NULL ,
>
[Number] [varchar] (50) NOT NULL ,
>
[TimeStamp] [smalldatetime] NOT NULL CONSTRAINT [DF_Table1_TimeStamp]
>
DEFAULT (getdate()),
>
CONSTRAINT [PK_Table1] PRIMARY KEY CLUSTERED
>
(
>
[Id]
>
) ON [PRIMARY]
>
) ON [PRIMARY]
>
GO
>
>
CREATE TABLE [Table2]
>
(
>
[Id] [int] IDENTITY (1, 1) NOT FOR REPLICATION NOT NULL ,
>
[Table1Id] [int] NOT NULL ,
>
[LingoId] [int] NOT NULL ,
>
[Header] [nvarchar] (150) NOT NULL ,
>
[Description] [ntext] NOT NULL ,
>
CONSTRAINT [PK_Table2] PRIMARY KEY CLUSTERED
>
(
>
[Id]
>
) ON [PRIMARY] ,
>
CONSTRAINT [FK_Table2_Table1] FOREIGN KEY
>
(
>
[Table1Id]
>
) REFERENCES [Table1] (
>
[Id]
>
)
>
) ON [PRIMARY] TEXTIMAGE_ON [PRIMARY]
>
GO
>


>
>
What I would like is that if LingoId = 2 in the query below doesn't exists
>
than it should fall thru and use the values where LingoId = 1. LingoId = 1
>
always exists for each Table2.Id. Is this doable?
>
>
code:

>
SELECT
>
dbo.Table1.Id,
>
dbo.Table1.Number,
>
dbo.Table1.[TimeStamp],
>
dbo.Table2.Header,
>
dbo.Table2.Description
>
FROM
>
dbo.Table1
>
LEFT OUTER JOIN
>
dbo.Table2 ON dbo.Table1.Id = dbo.Table2.Table1Id
>
WHERE
>
(dbo.Table2.LingoId = 2) --Something should happen here I quess.
>

|||First, you are filtering the result with values from table2. That will
effectively be an INNER JOIN. Did you mean it like that?
If you want to use only one query then something like this could be good
enough:
SELECT
dbo.Table1.Id,
dbo.Table1.Number,
dbo.Table1.[TimeStamp],
dbo.Table2.Header,
dbo.Table2.Description
FROM
dbo.Table1
LEFT OUTER JOIN
dbo.Table2 ON dbo.Table1.Id = dbo.Table2.Table1Id
WHERE
(dbo.Table2.LingoId = case when exists (select table1.id from table1
inner join table2 on table1.id = table2.id where table2.LingoID = 2) then 2
else 1 end)
MC
"Senna" <
Senna@.discussions.microsoft.com>
wrote in message
news:7335ADA4-EF90-4525-B513-ACD9F64CB353@.microsoft.com...
>
Have two tables:
>
>
code:

>
CREATE TABLE [Table1]
>
(
>
[Id] [int] IDENTITY (1, 1) NOT FOR REPLICATION NOT NULL ,
>
[Number] [varchar] (50) NOT NULL ,
>
[TimeStamp] [smalldatetime] NOT NULL CONSTRAINT [DF_Table1_TimeStamp]
>
DEFAULT (getdate()),
>
CONSTRAINT [PK_Table1] PRIMARY KEY CLUSTERED
>
(
>
[Id]
>
) ON [PRIMARY]
>
) ON [PRIMARY]
>
GO
>
>
CREATE TABLE [Table2]
>
(
>
[Id] [int] IDENTITY (1, 1) NOT FOR REPLICATION NOT NULL ,
>
[Table1Id] [int] NOT NULL ,
>
[LingoId] [int] NOT NULL ,
>
[Header] [nvarchar] (150) NOT NULL ,
>
[Description] [ntext] NOT NULL ,
>
CONSTRAINT [PK_Table2] PRIMARY KEY CLUSTERED
>
(
>
[Id]
>
) ON [PRIMARY] ,
>
CONSTRAINT [FK_Table2_Table1] FOREIGN KEY
>
(
>
[Table1Id]
>
) REFERENCES [Table1] (
>
[Id]
>
)
>
) ON [PRIMARY] TEXTIMAGE_ON [PRIMARY]
>
GO
>


>
>
What I would like is that if LingoId = 2 in the query below doesn't exists
>
than it should fall thru and use the values where LingoId = 1. LingoId = 1
>
always exists for each Table2.Id. Is this doable?
>
>
code:

>
SELECT
>
dbo.Table1.Id,
>
dbo.Table1.Number,
>
dbo.Table1.[TimeStamp],
>
dbo.Table2.Header,
>
dbo.Table2.Description
>
FROM
>
dbo.Table1
>
LEFT OUTER JOIN
>
dbo.Table2 ON dbo.Table1.Id = dbo.Table2.Table1Id
>
WHERE
>
(dbo.Table2.LingoId = 2) --Something should happen here I quess.
>

|||The solution, as I mention above, looked liked this:
SELECT
dbo.Table1.Id,
dbo.Table1.Number,
dbo.Table1.[TimeStamp],
dbo.Table2.Header,
dbo.Table2.Description
FROM
dbo.Table1
INNER JOIN
dbo.Table2 ON dbo.Table1.Id = dbo.Table2.Table1Id
WHERE
dbo.Table2.LingoId = 2
or (dbo.Table2.LingoId = 1
and not exists
(select *
from table2 cn
where cn.table1id = dbo.Table2.Table1Id
and cn.lingoid = 2))
ps. Thank for your time and answer Jens.
"Senna" wrote:

>
Have two tables:
>
>
code:

>
CREATE TABLE [Table1]
>
(
>
[Id] [int] IDENTITY (1, 1) NOT FOR REPLICATION NOT NULL ,
>
[Number] [varchar] (50) NOT NULL ,
>
[TimeStamp] [smalldatetime] NOT NULL CONSTRAINT [DF_Table1_TimeStamp]
>
DEFAULT (getdate()),
>
CONSTRAINT [PK_Table1] PRIMARY KEY CLUSTERED
>
(
>
[Id]
>
) ON [PRIMARY]
>
) ON [PRIMARY]
>
GO
>
>
CREATE TABLE [Table2]
>
(
>
[Id] [int] IDENTITY (1, 1) NOT FOR REPLICATION NOT NULL ,
>
[Table1Id] [int] NOT NULL ,
>
[LingoId] [int] NOT NULL ,
>
[Header] [nvarchar] (150) NOT NULL ,
>
[Description] [ntext] NOT NULL ,
>
CONSTRAINT [PK_Table2] PRIMARY KEY CLUSTERED
>
(
>
[Id]
>
) ON [PRIMARY] ,
>
CONSTRAINT [FK_Table2_Table1] FOREIGN KEY
>
(
>
[Table1Id]
>
) REFERENCES [Table1] (
>
[Id]
>
)
>
) ON [PRIMARY] TEXTIMAGE_ON [PRIMARY]
>
GO
>


>
>
What I would like is that if LingoId = 2 in the query below doesn't exists
>
than it should fall thru and use the values where LingoId = 1. LingoId = 1
>
always exists for each Table2.Id. Is this doable?
>
>
code:

>
SELECT
>
dbo.Table1.Id,
>
dbo.Table1.Number,
>
dbo.Table1.[TimeStamp],
>
dbo.Table2.Header,
>
dbo.Table2.Description
>
FROM
>
dbo.Table1
>
LEFT OUTER JOIN
>
dbo.Table2 ON dbo.Table1.Id = dbo.Table2.Table1Id
>
WHERE
>
(dbo.Table2.LingoId = 2) --Something should happen here I quess.
>

|||Yes, it was an inner join. :)
See the other post with the solution I went with. Thanks anyway for your
time and effort.
"MC" wrote:

> First, you are filtering the result with values from table2. That will
> effectively be an INNER JOIN. Did you mean it like that?
> If you want to use only one query then something like this could be good
> enough:
> SELECT
> dbo.Table1.Id,
> dbo.Table1.Number,
> dbo.Table1.[TimeStamp],
> dbo.Table2.Header,
> dbo.Table2.Description
> FROM
> dbo.Table1
> LEFT OUTER JOIN
> dbo.Table2 ON dbo.Table1.Id = dbo.Table2.Table1Id
> WHERE
> (dbo.Table2.LingoId = case when exists (select table1.id from table1
> inner join table2 on table1.id = table2.id where table2.LingoID = 2) then
2
> else 1 end)
>
> MC
>
> "Senna" <Senna@.discussions.microsoft.com> wrote in message
> news:7335ADA4-EF90-4525-B513-ACD9F64CB353@.microsoft.com...
>
>

Wednesday, March 7, 2012

Challenge - Swap two columns

Ok .. a challenge ...
How do you swap two columns based on some condition without using a cursor ( I mean a set based solution).alter table foo add tempcol

update foo set tempcol=field1

update foo set field1 = field2

update foo set field2=tempcol

alter table drop column tempcol

you did not say it had to be good, you did not say it had to be efficient, you said merely no cursor|||did you forget it is not possible to add a column and update it in the same sql batch ...|||forget? no, because i never knew that to begin with

okay, so just run those steps in separate batches|||forget? no, because i never knew that to begin with

You are joking ? Right ?|||not in the slightest, no, i was not joking

i don't know what a "batch" is

i just know it's something you DBAs concern yourself with

is a batch like a transaction block? isn't there a COMMIT statement you can use?|||not in the slightest, no, i was not joking

i don't know what a "batch" is

i just know it's something you DBAs concern yourself with

is a batch like a transaction block? isn't there a COMMIT statement you can use?
"Go" and Read up on "GO" statement in the holy book ...
Also
Try this

use pubs
go
create table Mytable99 (a int)
go
insert into Mytable99 select 1
go
begin tran
alter table MyTable99
add b int
commit tran
update MyTable99 set b = 2
go

Then Try this

drop table MyTable99
go
use pubs
go
create table Mytable99 (a int)
go
insert into Mytable99 select 1
go
begin tran
alter table MyTable99
add b int
commit tran
go
update MyTable99 set b = 2
go

drop table MyTable99
go|||Try this
use pubs
go
create table Mytable99 (a int)
go
insert into Mytable99 select 1
go
begin tran
alter table MyTable99
add b int
commit tran
update MyTable99 set b = 2
go

Error: Invalid column name 'b'. (State:S0022, Native Code: CF)

Then Try this
drop table MyTable99
go
use pubs
go
create table Mytable99 (a int)
go
insert into Mytable99 select 1
go
begin tran
alter table MyTable99
add b int
commit tran
go
update MyTable99 set b = 2
go

drop table MyTable99
go

This command did not return data, and it did not return any rows

sweet

and your point is?

and how does this swap two columns??????|||I am new to SQL Server so maybe I am misunderstanding the requirement but is there anything wrong with the following?

update table99 set a=b, b=a

with an optional where condition.|||I am new to SQL Server so maybe I am misunderstanding the requirement but is there anything wrong with the following?

update table99 set a=b, b=a

with an optional where condition. At least the way that I understand Enigma's question, your answer is exactly what I would have suggested. The part that I'm still fuzzy on is that the rest of this thread seems to have veered off on a tangent, which makes me wonder if I understood the original question.

-PatP|||That was the answer I was looking for ... coz I was intrigued by the way sql server handles updates in this case

R937 : the point is the sql batch ... all statements in a sql batch are compiled into one execution plan ... and you cannot alter and update in the same sql batch ... Transaction has no effect on a sql batch ...|||I am new to SQL Server so maybe I am misunderstanding the requirement but is there anything wrong with the following?

update table99 set a=b, b=a

with an optional where condition.

Not a shining moment for the gurus of dbforums.com...|||Yep. For those geeky enough to care, the ISO standard calls for all of the RValues in an UPDATE statement to evaluate before any of the LValues are resolved. This means that all of the computations have to be complete before the first change is allowed to happen.

-PatP

Sunday, February 12, 2012

CASTing a datatype returned by CASE Statement

I realize that the CASE statement doesn't like different datatypes as return values but if I want to format the "0" in the second WHEN condition below to "000", how do I do that? I have a "Region" that is "000" and would like it to show up that way at the very top of my report. I have the GROUP BY and ORDER BY to work fine, it just shows up as "0" and I can't change it. I realize it is being read as an int but am having trouble with the CAST and where to place it. Thanks again, you guys are great.

ddave

SELECT Region =
CASE WHEN branch_num IN(48,53,78,173,186,198,208,212,257,286,287,317,35 3,398,440,
478,571,572,610,1069) THEN 44
WHEN branch_num IN(484,532,841,864,7001,7101,7102,7103,7104,9031) THEN 0
ELSE 999
ENDThat depends (doesn't it always?) on what you really want. If you want the other regions to show using normal INT formatting, but 0 to be a special case That is one thing, if you want all the region numbers to be zero filled, that is something different. If you want something I haven't thought of yet, then that's probably different too.

The quick and dirty would be to use:SELECT Region =
CASE
WHEN branch_num IN(48,53,78,173,186,198,208,212,257,286,287,317,35 3,398,440,
478,571,572,610,1069) THEN ' 44'
WHEN branch_num IN(484,532,841,864,7001,7101,7102,7103,7104,9031) THEN '000'
ELSE '999'
END

-PatP|||Pat,

Once again, "You da Man!!". It works perfectly. I decided to use '000', ' 1', ' 78', etc. I spent over an hour on it and I knew it was something easy. I mean I don't expect a medal or anything but you can be lost w/o "the little details". Thanks again.

ddave|||If I want the format to show the Region field just once, is there a way to do that? My current report has a Region field immediately to the left of BranchNo. Branches are contained within the Regions. I got it to list Region every time I show a record but just in case the manager wants it formatted the way I mention I want to be prepared. The example I was to follow has Region just once.

This is an example of what I have now:

code:--------------------
Region BranchNo OrderNo ErrorCode1 ErrorCode2 ErrorCode3
000 478 111 0 1 1
000 478 112 0 0 0
000 478 113 1 0 0
001 610 119 0 0 0
001 610 120 1 0 0
----------------------

This is an example of what I wish to try:

code:--------------------
Region BranchNo OrderNo ErrorCode1 ErrorCode2 ErrorCode3
000 478 111 0 1 1
478 112 0 0 0
478 113 1 0 0
001 610 119 0 0 0
610 120 1 0 0
----------------------

ddave|||What reporting tool are you using? Hopefully this isn't 100% Transact-SQL based, right?

-PatP|||Well, I am looking at the data in Query Analyzer but that is a good question. I guess the real answer is that we haven't decided yet. I can use Access though I have to figure out the mechanics which I know won't be difficult. I can even stick it on an Excel spreadsheet as long as it looks good. I say Access because that is "what the others did" but it is not an issue.

ddave|||It's a presntation issue, and Access is very good at it, and can easily do what your asking...

I'd love to setup reporting services though...

Anyone seen it?

What's the installation like?

What's the interface?

Can you use the same box as sql server?

PS. If they say Crystal...run...|||Reporting Services is quite cool, but it is rather complex and it requires Visual Studio to develop reports.

MS-Access would be beauteous, and would make the formatting, grouping, etc rather simple. I'm not nearly as alergic to Crystal Reports as most folks around here seem to be, but I would STRONGLY advise using Access unless you have another tool of choice.

-PatP