April 27, 2009 at 12:18 pm
Adam Machanic (4/27/2009)
Florian Reischl (4/27/2009)
Thanks for the new version! I also supposed that a char array should perform better than the string. The current test results show the opposite though...Did you try my new version in your tests? Or are you referring to the char array solution already posted here? I'm assuming the latter since the test results you just posted appear to be unchanged from your previous post... Please give the new version a try. In my tests against my previous split method my new one is performing consistently 12-15% faster, both under load and in solitary tests on an empty server.
Er... *cough*
... it happened automatically! The voices told me to do it...
Apologize! I couldn't just copy paste the code from your page since the names didn't fit with my test environment. The first test environment I had in this thread became completely unusable because I copied all names of all functions. So I copied the code blocks but into own methods and I noticed the memory copies within your code and fixed it... Again, it happened automatically... Sorry!
Here my modified code:
using System;
using System.Collections;
using System.Data;
using System.Data.SqlClient;
using System.Data.SqlTypes;
using Microsoft.SqlServer.Server;
public partial class UserDefinedFunctions
{
[Microsoft.SqlServer.Server.SqlFunction(
FillRowMethodName="FillRow_SplitString_Enumerator",
TableDefinition="item nvarchar(max)"
)
]
public static IEnumerator ufn_clr_SplitString_Enumerator_FR(
[SqlFacet(
IsFixedLength=false,
IsNullable=false,
MaxSize=-1
)
]
SqlString strIn,
[SqlFacet(
IsFixedLength=true,
IsNullable=false,
MaxSize=1
)
]
SqlString delimiter
)
{
return new SplitStringEnumerator(strIn.Value, delimiter.Value[0]);
}
public static void FillRow_SplitString_Enumerator(object obj, out SqlString item)
{
item = new SqlString((string)obj);
}
public class SplitStringEnumerator : IEnumerator
{
public SplitStringEnumerator(string theString, char delimiter)
{
this._theString = theString;
this._delimiter = delimiter;
this._lastPos = -1;
this._nextPos = -1;
}
#region IEnumerator Members
public object Current
{
get { return _theString.Substring(_lastPos, _nextPos - _lastPos).Trim(); }
}
public bool MoveNext()
{
if (_nextPos >= _theString.Length)
return false;
else
{
_lastPos = _nextPos + 1;
if (_lastPos == _theString.Length)
return false;
_nextPos = _theString.IndexOf(_delimiter, _lastPos);
if (_nextPos == -1)
_nextPos = _theString.Length;
return true;
}
}
public void Reset()
{
this._lastPos = -1;
this._nextPos = -1;
}
#endregion
private int _lastPos;
private int _nextPos;
private string _theString;
private char _delimiter;
}
};
I added both of your methods to my tests (now without changes!). I named your first (from your page) "CLR String Enumerator Adam1" and the second (posted here) "CLR String Enumerator Adam2". My version is called "CLR String Enumerator FR".
Anyway, it still seems that the old works faster than the new one. I also will look a little bit deeper into both.
Results:
ItemLength ItemCount ItemRows ItemType ItemDescription Ranking Module Duration(ms) CpuTime
----------- ----------- ----------- -------------- ---------------- ------- ---------------------------- ------------ -------
10 10 10 VARCHAR(111) Fixed Length 1 Traditional Tally TOP(0) 00:00:00.003 15
10 10 10 VARCHAR(111) Fixed Length 2 CLR char loop 00:00:00.007 0
10 10 10 VARCHAR(111) Fixed Length 3 CLR Simple 00:00:00.007 16
10 10 10 VARCHAR(111) Fixed Length 4 CLR String Enumerator FR 00:00:00.007 15
10 10 10 VARCHAR(111) Fixed Length 5 CLR String Enumerator Adam1 00:00:00.007 0
10 10 10 VARCHAR(111) Fixed Length 6 CLR String Enumerator Adam2 00:00:00.007 16
10 10 10 VARCHAR(111) Fixed Length 7 CLR RegEx 00:00:00.010 0
10 10 10 VARCHAR(111) Fixed Length 8 CLR XML 00:00:00.043 16
10 10 10 VARCHAR(111) Fixed Length 9 Cursor 00:00:00.043 15
10 10 10 VARCHAR(111) Fixed Length 10 Traditional Tally 00:00:00.190 16
10 10 1000 VARCHAR(111) Fixed Length 1 Traditional Tally TOP(0) 00:00:00.133 125
10 10 1000 VARCHAR(111) Fixed Length 2 Traditional Tally 00:00:00.257 141
10 10 1000 VARCHAR(111) Fixed Length 3 CLR String Enumerator FR 00:00:00.403 390
10 10 1000 VARCHAR(111) Fixed Length 4 CLR String Enumerator Adam1 00:00:00.407 406
10 10 1000 VARCHAR(111) Fixed Length 5 CLR String Enumerator Adam2 00:00:00.440 453
10 10 1000 VARCHAR(111) Fixed Length 6 CLR char loop 00:00:00.440 437
10 10 1000 VARCHAR(111) Fixed Length 7 CLR Simple 00:00:00.447 437
10 10 1000 VARCHAR(111) Fixed Length 8 CLR RegEx 00:00:00.460 484
10 10 1000 VARCHAR(111) Fixed Length 9 CLR XML 00:00:00.637 577
10 10 1000 VARCHAR(111) Fixed Length 10 Cursor 00:00:00.687 718
10 10 10000 VARCHAR(111) Fixed Length 1 Traditional Tally TOP(0) 00:00:01.227 1217
10 10 10000 VARCHAR(111) Fixed Length 2 Traditional Tally 00:00:01.593 1311
10 10 10000 VARCHAR(111) Fixed Length 3 CLR String Enumerator FR 00:00:04.023 4181
10 10 10000 VARCHAR(111) Fixed Length 4 CLR String Enumerator Adam1 00:00:04.037 4134
10 10 10000 VARCHAR(111) Fixed Length 5 CLR String Enumerator Adam2 00:00:04.390 4509
10 10 10000 VARCHAR(111) Fixed Length 6 CLR char loop 00:00:04.400 4461
10 10 10000 VARCHAR(111) Fixed Length 7 CLR Simple 00:00:04.427 4539
10 10 10000 VARCHAR(111) Fixed Length 8 CLR RegEx 00:00:04.530 4649
10 10 10000 VARCHAR(111) Fixed Length 9 CLR XML 00:00:05.773 5491
10 10 10000 VARCHAR(111) Fixed Length 10 Cursor 00:00:06.607 6739
100 10 10 VARCHAR(1011) Fixed Length 1 CLR String Enumerator FR 00:00:00.007 15
100 10 10 VARCHAR(1011) Fixed Length 2 CLR String Enumerator Adam1 00:00:00.007 16
100 10 10 VARCHAR(1011) Fixed Length 3 CLR String Enumerator Adam2 00:00:00.007 0
100 10 10 VARCHAR(1011) Fixed Length 4 Traditional Tally TOP(0) 00:00:00.010 15
100 10 10 VARCHAR(1011) Fixed Length 5 CLR Simple 00:00:00.010 16
100 10 10 VARCHAR(1011) Fixed Length 6 CLR RegEx 00:00:00.010 0
100 10 10 VARCHAR(1011) Fixed Length 7 Cursor 00:00:00.013 16
100 10 10 VARCHAR(1011) Fixed Length 8 CLR char loop 00:00:00.027 16
100 10 10 VARCHAR(1011) Fixed Length 9 CLR XML 00:00:00.053 31
100 10 10 VARCHAR(1011) Fixed Length 10 Traditional Tally 00:00:00.503 16
100 10 100 VARCHAR(1011) Fixed Length 1 CLR String Enumerator FR 00:00:00.053 62
100 10 100 VARCHAR(1011) Fixed Length 2 CLR String Enumerator Adam1 00:00:00.057 47
100 10 100 VARCHAR(1011) Fixed Length 3 CLR String Enumerator Adam2 00:00:00.057 62
100 10 100 VARCHAR(1011) Fixed Length 4 CLR Simple 00:00:00.057 63
100 10 100 VARCHAR(1011) Fixed Length 5 CLR RegEx 00:00:00.057 47
100 10 100 VARCHAR(1011) Fixed Length 6 CLR char loop 00:00:00.083 47
100 10 100 VARCHAR(1011) Fixed Length 7 Traditional Tally TOP(0) 00:00:00.087 63
100 10 100 VARCHAR(1011) Fixed Length 8 CLR XML 00:00:00.093 62
100 10 100 VARCHAR(1011) Fixed Length 9 Cursor 00:00:00.123 93
100 10 100 VARCHAR(1011) Fixed Length 10 Traditional Tally 00:00:00.357 94
100 10 1000 VARCHAR(1011) Fixed Length 1 CLR String Enumerator FR 00:00:00.483 530
100 10 1000 VARCHAR(1011) Fixed Length 2 CLR String Enumerator Adam1 00:00:00.520 484
100 10 1000 VARCHAR(1011) Fixed Length 3 CLR String Enumerator Adam2 00:00:00.523 530
100 10 1000 VARCHAR(1011) Fixed Length 4 CLR Simple 00:00:00.527 577
100 10 1000 VARCHAR(1011) Fixed Length 5 CLR RegEx 00:00:00.557 546
100 10 1000 VARCHAR(1011) Fixed Length 6 Traditional Tally TOP(0) 00:00:00.627 655
100 10 1000 VARCHAR(1011) Fixed Length 7 CLR char loop 00:00:00.630 499
100 10 1000 VARCHAR(1011) Fixed Length 8 CLR XML 00:00:00.653 656
100 10 1000 VARCHAR(1011) Fixed Length 9 Cursor 00:00:00.847 874
100 10 1000 VARCHAR(1011) Fixed Length 10 Traditional Tally 00:00:00.920 686
100 10 100 NVARCHAR(1011) Fixed Length 1 CLR String Enumerator Adam1 00:00:00.050 63
100 10 100 NVARCHAR(1011) Fixed Length 2 CLR String Enumerator FR 00:00:00.053 62
100 10 100 NVARCHAR(1011) Fixed Length 3 CLR String Enumerator Adam2 00:00:00.057 62
100 10 100 NVARCHAR(1011) Fixed Length 4 CLR Simple 00:00:00.057 62
100 10 100 NVARCHAR(1011) Fixed Length 5 CLR RegEx 00:00:00.057 62
100 10 100 NVARCHAR(1011) Fixed Length 6 CLR char loop 00:00:00.077 47
100 10 100 NVARCHAR(1011) Fixed Length 7 Traditional Tally TOP(0) 00:00:00.093 78
100 10 100 NVARCHAR(1011) Fixed Length 8 CLR XML 00:00:00.100 78
100 10 100 NVARCHAR(1011) Fixed Length 9 Cursor 00:00:00.140 109
100 10 100 NVARCHAR(1011) Fixed Length 10 Traditional Tally 00:00:00.200 93
100 10 1000 NVARCHAR(1011) Fixed Length 1 CLR String Enumerator FR 00:00:00.483 514
100 10 1000 NVARCHAR(1011) Fixed Length 2 CLR String Enumerator Adam1 00:00:00.493 515
100 10 1000 NVARCHAR(1011) Fixed Length 3 CLR String Enumerator Adam2 00:00:00.527 578
100 10 1000 NVARCHAR(1011) Fixed Length 4 CLR RegEx 00:00:00.537 562
100 10 1000 NVARCHAR(1011) Fixed Length 5 CLR Simple 00:00:00.543 562
100 10 1000 NVARCHAR(1011) Fixed Length 6 CLR char loop 00:00:00.593 530
100 10 1000 NVARCHAR(1011) Fixed Length 7 Traditional Tally TOP(0) 00:00:00.723 733
100 10 1000 NVARCHAR(1011) Fixed Length 8 CLR XML 00:00:00.740 562
100 10 1000 NVARCHAR(1011) Fixed Length 9 Cursor 00:00:00.840 842
100 10 1000 NVARCHAR(1011) Fixed Length 10 Traditional Tally 00:00:01.270 780
1000 10 10 NVARCHAR(MAX) Fixed Length 1 CLR Simple 00:00:00.010 16
1000 10 10 NVARCHAR(MAX) Fixed Length 2 CLR RegEx 00:00:00.010 0
1000 10 10 NVARCHAR(MAX) Fixed Length 3 CLR String Enumerator FR 00:00:00.010 16
1000 10 10 NVARCHAR(MAX) Fixed Length 4 CLR String Enumerator Adam1 00:00:00.010 15
1000 10 10 NVARCHAR(MAX) Fixed Length 5 CLR String Enumerator Adam2 00:00:00.010 16
1000 10 10 NVARCHAR(MAX) Fixed Length 6 CLR char loop 00:00:00.047 0
1000 10 10 NVARCHAR(MAX) Fixed Length 7 CLR XML 00:00:00.050 15
1000 10 10 NVARCHAR(MAX) Fixed Length 8 Cursor 00:00:00.053 31
1000 10 10 NVARCHAR(MAX) Fixed Length 9 Traditional Tally TOP(0) 00:00:00.540 515
1000 10 10 NVARCHAR(MAX) Fixed Length 10 Traditional Tally 00:00:00.833 499
1000 10 100 NVARCHAR(MAX) Fixed Length 1 CLR String Enumerator FR 00:00:00.090 78
1000 10 100 NVARCHAR(MAX) Fixed Length 2 CLR Simple 00:00:00.097 78
1000 10 100 NVARCHAR(MAX) Fixed Length 3 CLR String Enumerator Adam2 00:00:00.097 78
1000 10 100 NVARCHAR(MAX) Fixed Length 4 CLR char loop 00:00:00.107 78
1000 10 100 NVARCHAR(MAX) Fixed Length 5 CLR RegEx 00:00:00.113 78
1000 10 100 NVARCHAR(MAX) Fixed Length 6 CLR String Enumerator Adam1 00:00:00.150 62
1000 10 100 NVARCHAR(MAX) Fixed Length 7 CLR XML 00:00:00.153 156
1000 10 100 NVARCHAR(MAX) Fixed Length 8 Cursor 00:00:00.313 250
1000 10 100 NVARCHAR(MAX) Fixed Length 9 Traditional Tally TOP(0) 00:00:04.977 5148
1000 10 100 NVARCHAR(MAX) Fixed Length 10 Traditional Tally 00:00:05.323 5054
Greets
Flo
April 27, 2009 at 12:38 pm
Hmm, something you've changed is making your version an order of magnitude slower on my test system than either of my versions. Here's a simple test I'm running:
--Set up a test table
create table #z (y varchar(max))
insert #z select replicate(convert(varchar(max), 'abcd,'), 1000000)
--Wall clock time for each of the methods
--Adam1
declare @d datetime
set @d = getdate()
select count(*) from #z
cross apply dbo.faster_split(y, ',') q
select datediff(ms, @d, getdate()) AS Adam1
go
--Adam2
declare @d datetime
set @d = getdate()
select count(*) from #z
cross apply dbo.even_faster(y, ',') q
select datediff(ms, @d, getdate()) AS Adam2
go
--FR
declare @d datetime
set @d = getdate()
select count(*) from #z
cross apply dbo.ufn_clr_SplitString_Enumerator_FR(y, ',') q
select datediff(ms, @d, getdate()) AS FR
go
Results, on my SQL Server 2008 server:
Adam1: ~1350
Adam2: ~1100
FR: ~13000 (that additional zero is not a typo)
Odd...
--
Adam Machanic
whoisactive
April 27, 2009 at 12:40 pm
Adam Machanic (4/27/2009)
Hmm, something you've changed is making your version an order of magnitude slower on my test system than either of my versions.
OK, found it. Make your return type NVARCHAR(4000), not NVARCHAR(MAX). And while you're at it, ditch that _ syntax for locals, please for the love of readable code!!! 🙂
--
Adam Machanic
whoisactive
April 27, 2009 at 12:50 pm
Really strange...
I copied exactly your script (just changed the names of the functions):
Adam1: 15546
Adam2: 15380
FR: 15550
System:
Microsoft SQL Server 2008 (SP1) - 10.0.2531.0 (X64)
Mar 29 2009 10:11:52
Copyright (c) 1988-2008 Microsoft Corporation
Developer Edition (64-bit) on Windows NT 6.0 <X64> (Build 6001: Service Pack 1)
Do you have any explanation??
Greets
Flo
April 27, 2009 at 12:54 pm
15 seconds? Time for a new computer!
--
Adam Machanic
whoisactive
April 27, 2009 at 12:54 pm
Adam Machanic (4/27/2009)
Adam Machanic (4/27/2009)
Hmm, something you've changed is making your version an order of magnitude slower on my test system than either of my versions.OK, found it. Make your return type NVARCHAR(4000), not NVARCHAR(MAX). And while you're at it, ditch that _ syntax for locals, please for the love of readable code!!! 🙂
😀
I really like the _syntax to distinguish between local and module variables. Would you prefer m_anything? :laugh:
Greets
Flo
April 27, 2009 at 12:57 pm
Adam Machanic (4/27/2009)
15 seconds? Time for a new computer!
I think Core2 Quad 2,4 is not so bad 😉
All three methods use nvarchar(max). Copy paste error. Sorry again!
Changed all to nvarchar(4000):
Adadm1: 1220
Adam2: 1160
FR: 1210
Greets
Flo
April 27, 2009 at 1:01 pm
Florian Reischl (4/27/2009)
I really like the _syntax to distinguish between local and module variables. Would you prefer m_anything?
Personally I like Pascal case for externally-facing variables and camel case for local and member variables. I didn't follow that standard too well in these examples but it's what I normally use and I find it to be quite nice for my purposes.
Glad to hear you got the NVARCHAR issues sorted. I just load tested your mods to my original code and it looks like it's the current winner by a small margin.
--
Adam Machanic
whoisactive
April 27, 2009 at 1:22 pm
Hi Adam
Adam Machanic (4/27/2009)
Florian Reischl (4/27/2009)
I really like the _syntax to distinguish between local and module variables. Would you prefer m_anything?Personally I like Pascal case for externally-facing variables and camel case for local and member variables. I didn't follow that standard too well in these examples but it's what I normally use and I find it to be quite nice for my purposes.
Yeah, I also like the CamelCase! I use it for different words. I just distinguish between properties and public variables which start with an upper first character and local/module variables which start with a lower first character. I'm coming from the C/C++ side 😉
Glad to hear you got the NVARCHAR issues sorted.
Yepp!
I just load tested your mods to my original code and it looks like it's the current winner by a small margin.
I did not yet load tests but I have a new enumerator based solution which performs better than all the others on my system. Could you please try on your system?
using System;
using System.Collections;
using System.Data;
using System.Data.SqlClient;
using System.Data.SqlTypes;
using Microsoft.SqlServer.Server;
public partial class UserDefinedFunctions
{
[Microsoft.SqlServer.Server.SqlFunction(
FillRowMethodName="FillRow_SplitString_Enumerator_Flo2",
TableDefinition="item nvarchar(4000)"
)
]
public static IEnumerator ufn_clr_SplitString_Enumerator_Flo2(
[SqlFacet(
IsFixedLength=false,
IsNullable=false,
MaxSize=-1
)
]
SqlChars strIn,
[SqlFacet(
IsFixedLength=false,
IsNullable=false,
MaxSize=255
)
]
SqlChars delimiter
)
{
return new SplitStringEnumeratorFlo2(strIn.Value, delimiter.Value);
}
public static void FillRow_SplitString_Enumerator_Flo2(object obj, out SqlString item)
{
item = new SqlString((string)obj);
}
public class SplitStringEnumeratorFlo2 : IEnumerator
{
public SplitStringEnumeratorFlo2(char[] theString, char[] delimiter)
{
_theString = theString;
_delimiter = delimiter;
_delimiterLength = delimiter.Length;
_lastPos = 0;
_nextPos = _delimiterLength * -1;
}
#region IEnumerator Members
public object Current
{
get
{
return new string(_theString, _lastPos, _nextPos - _lastPos);
}
}
public bool MoveNext()
{
if (_nextPos >= _theString.Length)
return false;
else
{
_lastPos = _nextPos + _delimiterLength;
for (int i = _lastPos; i _theString.Length)
{
return false;
}
else
{
bool matches = true;
for (int j = 1; j < _delimiterLength; j++)
{
if (_theString != _delimiter[j])
{
matches = false;
break;
}
}
if (matches)
{
_nextPos = i + _delimiterLength;
return true;
}
}
}
}
_lastPos = _nextPos + _delimiterLength;
_nextPos = _theString.Length;
return true;
}
}
public void Reset()
{
_lastPos = -1;
_nextPos = -1;
}
#endregion
private int _lastPos;
private int _nextPos;
private char[] _theString;
private char[] _delimiter;
private int _delimiterLength;
}
};
For your test environment:
--Flo2
declare @d datetime
set @d = getdate()
select count(*) from #z
cross apply dbo.ufn_clr_SplitString_Enumerator_Flo2(y, ',') q
select datediff(ms, @d, getdate()) AS Flo2
go
Greets
Flo
April 27, 2009 at 1:32 pm
It does appear to be faster for a single delimiter, but it doesn't work properly for multiple delimiters:
select * from dbo.ufn_clr_SplitString_Enumerator_Flo2('a,,b', ',,') q
--
Adam Machanic
whoisactive
April 27, 2009 at 1:46 pm
Bug in row 98... Thanks!
Either replace:
_nextPos = i + _delimiterLength;
With:
_nextPos = i; // +_delimiterLength;
Or just copy paste the complete new:
using System;
using System.Collections;
using System.Data;
using System.Data.SqlClient;
using System.Data.SqlTypes;
using Microsoft.SqlServer.Server;
public partial class UserDefinedFunctions
{
[Microsoft.SqlServer.Server.SqlFunction(
FillRowMethodName="FillRow_SplitString_Enumerator_Flo2",
TableDefinition="item nvarchar(4000)"
)
]
public static IEnumerator ufn_clr_SplitString_Enumerator_Flo2(
[SqlFacet(
IsFixedLength=false,
IsNullable=false,
MaxSize=-1
)
]
SqlChars strIn,
[SqlFacet(
IsFixedLength=false,
IsNullable=false,
MaxSize=255
)
]
SqlChars delimiter
)
{
return new SplitStringEnumeratorFlo2(strIn.Value, delimiter.Value);
}
public static void FillRow_SplitString_Enumerator_Flo2(object obj, out SqlString item)
{
item = new SqlString((string)obj);
}
public class SplitStringEnumeratorFlo2 : IEnumerator
{
public SplitStringEnumeratorFlo2(char[] theString, char[] delimiter)
{
_theString = theString;
_delimiter = delimiter;
_delimiterLength = delimiter.Length;
_lastPos = 0;
_nextPos = _delimiterLength * -1;
}
#region IEnumerator Members
public object Current
{
get
{
return new string(_theString, _lastPos, _nextPos - _lastPos);
}
}
public bool MoveNext()
{
if (_nextPos >= _theString.Length)
return false;
else
{
_lastPos = _nextPos + _delimiterLength;
for (int i = _lastPos; i _theString.Length)
{
return false;
}
else
{
bool matches = true;
for (int j = 1; j < _delimiterLength; j++)
{
if (_theString != _delimiter[j])
{
matches = false;
break;
}
}
if (matches)
{
_nextPos = i; // +_delimiterLength;
return true;
}
}
}
}
_lastPos = _nextPos + _delimiterLength;
_nextPos = _theString.Length;
return true;
}
}
public void Reset()
{
_lastPos = -1;
_nextPos = -1;
}
#endregion
private int _lastPos;
private int _nextPos;
private char[] _theString;
private char[] _delimiter;
private int _delimiterLength;
}
};
Greets
Flo
April 27, 2009 at 2:02 pm
Can you please post the SQL build script for this CLR function, please. I'm stuck with my ...
CREATE FUNCTION ....
bit.
..and I bet most people who are trying to follow this lot are too!
Best wishes,
Phil Factor
April 27, 2009 at 2:14 pm
Adam Machanic (4/27/2009)
Hi all,I have posted a more scalable SQLCLR string split method here:
Thanks to Paul White for pointing me to this thread. Please consider testing all of these methods UNDER LOAD, using either SQLQueryStress, as I did, or another load tool. The results will be quite interesting, I promise. 😀
I'm glad Paul pointed you here. I was planning on pointing Flo to your blog post if no one else had.
Jack Corbett
Consultant - Straight Path Solutions
Check out these links on how to get faster and more accurate answers:
Forum Etiquette: How to post data/code on a forum to get the best help
Need an Answer? Actually, No ... You Need a Question
April 27, 2009 at 2:24 pm
Jack Corbett (4/27/2009)
Adam Machanic (4/27/2009)
Hi all,I have posted a more scalable SQLCLR string split method here:
Thanks to Paul White for pointing me to this thread. Please consider testing all of these methods UNDER LOAD, using either SQLQueryStress, as I did, or another load tool. The results will be quite interesting, I promise. 😀
I'm glad Paul pointed you here. I was planning on pointing Flo to your blog post if no one else had.
Hi Jack
Thank you! I'm also glad that this great CLR guy joined the discussion! His input was very important! The technical and the point that load tests are still missing.
Greets
Flo
April 27, 2009 at 2:25 pm
Phil Factor (4/27/2009)
Can you please post the SQL build script for this CLR function, please. I'm stuck with my ...CREATE FUNCTION ....
bit.
..and I bet most people who are trying to follow this lot are too!
Hi Phil
Sorry, but I think I cannot. Currently I have only a x64 system. If you have a x64 system, sure!
Greets
Flo
Viewing 15 posts - 256 through 270 (of 522 total)
You must be logged in to reply to this topic. Login to reply