varchar (max) 변수의 최대 크기
과거에 누군가가 .NET의 최대 크기를 물었다 varchar(max)
면 2GB라고 말했거나 더 정확한 수치 (2 ^ 31-1 또는 2147483647)를 찾아봤을 것 입니다.
그러나 최근 테스트에서 varchar(max)
변수가이 크기를 분명히 초과 할 수 있음을 발견했습니다 .
create table T (
Val1 varchar(max) not null
)
go
declare @KMsg varchar(max) = REPLICATE('a',1024);
declare @MMsg varchar(max) = REPLICATE(@KMsg,1024);
declare @GMsg varchar(max) = REPLICATE(@MMsg,1024);
declare @GGMMsg varchar(max) = @GMsg + @GMsg + @MMsg;
select LEN(@GGMMsg)
insert into T(Val1) select @GGMMsg
select LEN(Val1) from T
결과 :
(no column name)
2148532224
(1 row(s) affected)
Msg 7119, Level 16, State 1, Line 6
Attempting to grow LOB beyond maximum allowed size of 2147483647 bytes.
The statement has been terminated.
(no column name)
(0 row(s) affected)
이제 변수 가 2GB 장벽을 초과 할 수 있다는 것을 알고 있다면 변수에 대한 실제 제한이 무엇인지 아는 사람이 varchar(max)
있습니까?
(위의 테스트는 SQL Server 2008 (R2 아님)에서 완료되었습니다. 다른 버전에도 적용되는지 알고 싶습니다.)
내가 말할 수있는 한 2008 년에는 상한선이 없습니다.
SQL Server 2005에서 질문의 코드는 다음 @GGMMsg
과 같은 변수 할당에 실패합니다.
허용되는 최대 크기 인 2,147,483,647 바이트를 초과하여 LOB를 늘리려 고합니다.
아래 코드는 실패합니다
REPLICATE : 결과 길이가 대상 대형 유형의 길이 제한 (2GB)을 초과합니다.
그러나 이러한 제한은 조용히 해제 된 것으로 보입니다. 2008 년
DECLARE @y VARCHAR(MAX) = REPLICATE(CAST('X' AS VARCHAR(MAX)),92681);
SET @y = REPLICATE(@y,92681);
SELECT LEN(@y)
보고
8589767761
32 비트 데스크톱 컴퓨터에서 실행 했으므로이 8GB 문자열은 주소 지정 가능한 메모리를 초과합니다.
달리는
select internal_objects_alloc_page_count
from sys.dm_db_task_space_usage
WHERE session_id = @@spid
반환 됨
internal_objects_alloc_page_co
------------------------------
2144456
그래서이 모든 것이 길이에 대한 유효성 검사없이 LOB
페이지에 저장된다고 가정합니다 tempdb
. 페이지 수 증가는 모두 SET @y = REPLICATE(@y,92681);
문과 관련이 있습니다. 초기 변수 할당 @y
과 LEN
계산은 이것을 증가시키지 않았습니다.
The reason for mentioning this is because the page count is hugely more than I was expecting. Assuming an 8KB page then this works out at 16.36 GB which is obviously more or less double what would seem to be necessary. I speculate that this is likely due to the inefficiency of the string concatenation operation needing to copy the entire huge string and append a chunk on to the end rather than being able to add to the end of the existing string. Unfortunately at the moment the .WRITE
method isn't supported for varchar(max) variables.
Addition
I've also tested the behaviour with concatenating nvarchar(max) + nvarchar(max)
and nvarchar(max) + varchar(max)
. Both of these allow the 2GB limit to be exceeded. Trying to then store the results of this in a table then fails however with the error message Attempting to grow LOB beyond maximum allowed size of 2147483647 bytes.
again. The script for that is below (may take a long time to run).
DECLARE @y1 VARCHAR(MAX) = REPLICATE(CAST('X' AS VARCHAR(MAX)),2147483647);
SET @y1 = @y1 + @y1;
SELECT LEN(@y1), DATALENGTH(@y1) /*4294967294, 4294967292*/
DECLARE @y2 NVARCHAR(MAX) = REPLICATE(CAST('X' AS NVARCHAR(MAX)),1073741823);
SET @y2 = @y2 + @y2;
SELECT LEN(@y2), DATALENGTH(@y2) /*2147483646, 4294967292*/
DECLARE @y3 NVARCHAR(MAX) = @y2 + @y1
SELECT LEN(@y3), DATALENGTH(@y3) /*6442450940, 12884901880*/
/*This attempt fails*/
SELECT @y1 y1, @y2 y2, @y3 y3
INTO Test
EDIT: After further investigation, my original assumption that this was an anomaly (bug?) of the declare @var datatype = value
syntax is incorrect.
I modified your script for 2005 since that syntax is not supported, then tried the modified version on 2008. In 2005, I get the Attempting to grow LOB beyond maximum allowed size of 2147483647 bytes.
error message. In 2008, the modified script is still successful.
declare @KMsg varchar(max); set @KMsg = REPLICATE('a',1024);
declare @MMsg varchar(max); set @MMsg = REPLICATE(@KMsg,1024);
declare @GMsg varchar(max); set @GMsg = REPLICATE(@MMsg,1024);
declare @GGMMsg varchar(max); set @GGMMsg = @GMsg + @GMsg + @MMsg;
select LEN(@GGMMsg)
참고URL : https://stackoverflow.com/questions/7611394/maximum-size-of-a-varcharmax-variable
'program story' 카테고리의 다른 글
git push.default = current와 push.default = upstream의 차이점은 무엇입니까? (0) | 2020.09.17 |
---|---|
주소 유효성 검사를 어떻게 수행합니까? (0) | 2020.09.17 |
.NET 데스크톱 앱의 Settings.settings 대 app.config (0) | 2020.09.17 |
PHP 5.4.0 이전의 익명 함수에서`$ this` 사용 (0) | 2020.09.17 |
JQuery에서 클릭 한 요소를 제외한 모든 클래스를 선택하는 방법은 무엇입니까? (0) | 2020.09.16 |