ฟังก์ชัน PadLeft ใน T-SQL


113

ฉันมีตาราง A ต่อไปนี้:

id
----
1
2
12
123
1234

ฉันต้องการวางค่าทางซ้ายidด้วยศูนย์:

id
----
0001
0002
0012
0123
1234

ฉันจะบรรลุเป้าหมายนี้ได้อย่างไร?

คำตอบ:


197

ฉันเชื่อว่านี่อาจเป็นสิ่งที่คุณกำลังมองหา:

SELECT padded_id = REPLACE(STR(id, 4), SPACE(1), '0') 

FROM tableA

หรือ

SELECT REPLACE(STR(id, 4), SPACE(1), '0') AS [padded_id]

FROM tableA

ฉันยังไม่ได้ทดสอบไวยากรณ์ในตัวอย่างที่ 2 ฉันไม่แน่ใจว่ามันใช้งานได้ 100% หรือไม่ - อาจต้องมีการปรับแต่งบ้าง - แต่มันบ่งบอกถึงแนวคิดทั่วไปเกี่ยวกับวิธีการรับผลลัพธ์ที่คุณต้องการ

แก้ไข

เพื่อจัดการกับข้อกังวลที่ระบุไว้ในความคิดเห็น ...

@ pkr298 - ใช่ STR ทำงานเฉพาะกับตัวเลข ... ฟิลด์ OP คือ ID ... ดังนั้นตัวเลขเท่านั้น

@Desolator - แน่นอนว่าจะไม่ทำงาน ... พารามิเตอร์ตัวแรกมีความยาว 6 อักขระ คุณสามารถทำสิ่งต่างๆเช่น:

SELECT REPLACE(STR(id,
(SELECT LEN(MAX(id)) + 4 FROM tableA)), SPACE(1), '0') AS [padded_id] FROM tableA

ในทางทฤษฎีควรย้ายเสาประตู ... เมื่อจำนวนมากขึ้นก็ควรจะทำงานเสมอ .... ไม่ว่าจะเป็น 1 หรือ 123456789 ...

ดังนั้นหากค่าสูงสุดของคุณคือ 123456 ... คุณจะเห็น 0000123456 และถ้าค่าต่ำสุดของคุณคือ 1 คุณจะเห็น 0000000001


4
STR () ใช้ได้เฉพาะกับตัวเลข (หรือตัวเลขในช่องสตริง) รหัสนี้จะแตกหากคุณใช้งานบนฟิลด์ varchar ที่คุณคิดว่ามีตัวเลข แต่หนึ่งในระเบียนมีข้อมูลที่ไม่ถูกต้อง (ไม่ใช่ตัวเลข) ฟังก์ชัน RIGHT () จะไม่พังในกรณีนี้
pkr298

1
ฟังก์ชัน STR () จะไม่ทำงานหากตัวเลขมีความยาวมากขึ้น (เช่นSTR(123456, 4)จะกลับมา****

2
@Desolator ฉันได้เพิ่มการตอบสนองและแก้ไขเพื่ออำนวยความสะดวกในสถานการณ์ที่คุณเพิ่ม
Patrick

67

ขณะนี้ SQL Server สนับสนุนฟังก์ชันFORMATตั้งแต่เวอร์ชัน 2012 ดังนั้น:

SELECT FORMAT(id, '0000') FROM TableA

จะทำเคล็ดลับ

หากรหัสหรือคอลัมน์ของคุณอยู่ใน a varcharและแสดงถึงตัวเลขที่คุณแปลงก่อน:

SELECT FORMAT(CONVERT(INT,id), '0000') FROM TableA

เรียบง่ายขอบคุณ! เมื่อพิจารณาถึงวันที่ของคำถามเดิมตอนนี้ควรเป็นคำตอบอย่างเป็นทางการแล้ว;)
David Gunderson

1
หาก id เป็นสตริงคุณสามารถแปลงเป็นจำนวนเต็มก่อน - เลือกรูปแบบ (แปลง (int, id), '0000')
CrimsonKing

ขออภัยฉันไม่ลงคะแนนเพราะวิธีนี้ช้าจริงๆ ใช้เวลาสี่วินาทีในการรันมากกว่า 90 แถวในขณะที่คำตอบที่ได้รับการยอมรับคือทันที นี่เป็นข้อเสียที่สำคัญมากและควรใช้ FORMAT กับหนึ่งหรือสองระเบียนเท่านั้น มิฉะนั้นจะไม่มีประโยชน์เนื่องจากประสิทธิภาพที่แย่มาก
Shadow Wizard is Ear For You

@ShadowWizard ฉันเห็นประสิทธิภาพทันทีโดยใช้ FORMAT กับ 1,000 แถว
JohnnyHK

@JohnnyHK อาจจะมีบางอย่างกับการออกแบบตารางหรือเรื่องแปลก ๆ แต่ก็ยัง ... ความจริงก็คือสำหรับฉันมันช้ามากในขณะที่วิธีอื่นก็เร็ว
Shadow Wizard is Ear For You


43

โพสต์เก่า แต่อาจช่วยใครบางคนได้:

ในการดำเนินการจนจบด้วยอักขระที่ไม่เว้นว่าง 4 ตัว:

SELECT RIGHT ('0000'+COLUMNNAME, 4) FROM TABLENAME;

ให้เสร็จสิ้นจนถึง 10:

SELECT RIGHT ('0000000000'+COLUMNNAME, 10) FROM TABLENAME;

ในกรณีที่คอลัมน์เป็นตัวเลขให้แปลงเป็น varchar ก่อนด้วยรหัสดังกล่าว:

Select RIGHT('0000'+Convert(nvarchar(20), COLUMNNAME), 4)
From TABLENAME

และดำเนินการจนครบ 10 ด้วยฟิลด์ตัวเลข:

SELECT RIGHT ('0000000000'+Convert(nvarchar(20), COLUMNNAME), 10) FROM TABLENAME;

1
@ SilverM-A ไม่มียูทิลิตี้ที่จะเพิ่ม 0 ก่อนหน้าตัวเลขเนื่องจากจะถูกละเว้น (0003 คือ 3 หลังจากทั้งหมด) สิ่งที่คุณต้องการทำให้สำเร็จคือการโยนตัวเลขนั้นเป็นสตริง (varchar) จากนั้นใช้ข้อความข้างต้น
Marcelo Myara

1
@ SilverM-A หากเป็นเช่นนั้นให้แคสโดยใช้คำสั่ง "CAST" เช่น: SELECT RIGHT ('0000000000' + CAST (COLUMNNAME AS VARCHAR), 10) จาก TABLENAME; มันคืออะไร?
Marcelo Myara

@MarceloMyara นี่ควรเป็นส่วนหนึ่งของคำตอบไม่ใช่แค่ความคิดเห็น เพิ่มตอนนี้ตัวเอง
Shadow Wizard is Ear For You

หมายเหตุ: นี่เป็นคำตอบที่มีประสิทธิภาพที่สุดโดยไม่มีฟังก์ชันแฟนซีที่อาจทำงานช้า ดังนั้นฉันจึงให้รางวัลพิเศษ
Shadow Wizard is Ear For You


8

- โปรดตรวจสอบสิ่งเหล่านี้

select FORMAT(1, 'd4');
select FORMAT(2, 'd4');
select FORMAT(12, 'd4');
select FORMAT(123, 'd4');
select FORMAT(1234, 'd4');

- ฉันหวังว่าสิ่งเหล่านี้จะช่วยคุณได้


1
พร้อมใช้งานตั้งแต่ SQL Server 2012: msdn.microsoft.com/en-us/library/hh213505.aspx
Styxxy

5

ใช้ได้กับสตริงจำนวนเต็มและตัวเลข:

SELECT CONCAT(REPLICATE('0', 4 - LEN(id)), id)

4ความยาวที่ต้องการคือที่ไหน ธิสำหรับตัวเลขที่มีมากกว่า 4 หลักกลับสตริงที่ว่างเปล่าในNULLค่า


3

หากยังมีคนสนใจฉันพบบทความนี้ใน DATABASE.GUIDE:
Left Padding ใน SQL Server - 3 LPAD () Equivalents

กล่าวโดยย่อมี 3 วิธีที่กล่าวถึงในบทความนั้น
สมมติว่า id = 12 ของคุณและคุณต้องการให้แสดงเป็น 0012

วิธีที่ 1 - ใช้ฟังก์ชัน RIGHT ()
วิธีแรกใช้ฟังก์ชัน RIGHT () เพื่อส่งคืนเฉพาะส่วนขวาสุดของสตริงหลังจากเพิ่มศูนย์นำหน้าบางส่วน

SELECT RIGHT('00' + '12', 4);

ผลลัพธ์:
0012

วิธีที่ 2 - ใช้ชุดค่าผสมของ RIGHT () และ REPLICATE ()
วิธีนี้เกือบจะเหมือนกับวิธีก่อนหน้านี้โดยมีข้อแตกต่างเพียงอย่างเดียวคือฉันเพียงแค่แทนที่เลขศูนย์ทั้งสามด้วยฟังก์ชัน REPLICATE ():

SELECT RIGHT(REPLICATE('0', 2) + '12', 4);

ผลลัพธ์:
0012

วิธีที่ 3 - ใช้การรวมกันของ REPLACE () และ STR ()
วิธีนี้มาจากมุมที่แตกต่างกันอย่างสิ้นเชิงกับวิธีการก่อนหน้านี้:

SELECT REPLACE(STR('12', 4),' ','0');

ผลลัพธ์:
0012

ตรวจสอบบทความมีการวิเคราะห์เชิงลึกพร้อมตัวอย่างเพิ่มเติม


2

นี่คือสิ่งที่ฉันใช้ตามปกติเมื่อฉันต้องเติมค่า

SET @PaddedValue = REPLICATE('0', @Length - LEN(@OrigValue)) + CAST(@OrigValue as VARCHAR)

1

ฉันต้องการสิ่งนี้ในฟังก์ชันบนเซิร์ฟเวอร์ SQL และปรับคำตอบของแพทริคเล็กน้อย

declare @dossierId int = 123
declare @padded_id varchar(7)


set @padded_id = REPLACE(
              SPACE(7 - LEN(@dossierId)) + convert(varchar(7), @dossierId), 
              SPACE(1),  
              '0') 

SELECT @dossierId as '@dossierId'
      ,SPACE(LEN(@dossierId)) + convert(varchar(7)
      ,@dossierId) as withSpaces
      ,@padded_id as '@padded_id'

1

สร้างฟังก์ชัน:

    Create FUNCTION [dbo].[PadLeft]
      (
        @Text NVARCHAR(MAX) ,
        @Replace NVARCHAR(MAX) ,
        @Len INT
      )
RETURNS NVARCHAR(MAX)
AS
    BEGIN 


        DECLARE @var NVARCHAR(MAX) 

        SELECT @var = ISNULL(LTRIM(RTRIM(@Text)) , '')


        RETURN   RIGHT(REPLICATE(@Replace,@Len)+ @var, @Len)


    END

ตัวอย่าง:

Select dbo.PadLeft('123456','0',8)

เพียงประเด็นเกี่ยวกับมาตรฐานฉันจะไม่กังวลกับการตรวจสอบ IsNull หากค่าเป็นโมฆะฟังก์ชันควรจะคืนค่า null สำหรับค่านั้นเนื่องจากเป็นพฤติกรรมมาตรฐานสำหรับฟังก์ชันในตัว หากเราแปลงทุกอย่างเป็นค่าที่ไม่ใช่ค่าว่างผู้เรียกจะไม่สามารถใช้การดำเนินการลอจิกที่เป็นโมฆะได้อีกต่อไป (Null ในหลาย ๆ ตารางของฉันหมายถึง 'ไม่ระบุ' และควรใช้ค่าเริ่มต้นSELECT @var = LTRIM(RTRIM(@Text))
Chris Schaller

1

ฉันสร้างฟังก์ชัน:

CREATE FUNCTION [dbo].[fnPadLeft](@int int, @Length tinyint)
RETURNS varchar(255) 
AS 
BEGIN
    DECLARE @strInt varchar(255)

    SET @strInt = CAST(@int as varchar(255))
    RETURN (REPLICATE('0', (@Length - LEN(@strInt))) + @strInt);
END;

ใช้: เลือก dbo.fnPadLeft (123, 10)

ผลตอบแทน: 0000000123


0

สิ่งที่เป็นไปตามข้อกำหนด ODBC หากจำเป็นอาจมีดังต่อไปนี้:

select ifnull(repeat('0', 5 - (floor(log10(FIELD_NAME)) + 1)), '')
        + cast (FIELD as varchar(10))
  from TABLE_NAME

สิ่งนี้ขึ้นอยู่กับความจริงที่ว่าจำนวนของตัวเลขฐาน 10 สามารถพบได้โดยส่วนประกอบที่สำคัญของบันทึก จากนี้เราสามารถลบออกจากความกว้างของช่องว่างที่ต้องการได้ ซ้ำจะกลับnullค่าต่ำกว่า 1 ifnullดังนั้นเราจึงจำเป็น


0

วิธีแก้ปัญหาของฉันไม่ได้ผล แต่ช่วยฉันได้ในสถานการณ์ที่ค่า (หมายเลขเช็คธนาคารและหมายเลขอ้างอิงการโอนเงิน) ถูกจัดเก็บเป็น varchar ซึ่งบางรายการมีค่าตัวเลขตัวอักษรและฉันต้องเพิ่มความยาวหากความยาวน้อยกว่า 6 ตัวอักษร

คิดว่าจะแบ่งปันถ้ามีคนเจอสถานการณ์เดียวกัน

declare @minlen int = 6
declare @str varchar(20)

set @str = '123'
select case when len(@str) < @minlen then REPLICATE('0',@minlen-len(@str))+@str else @str end
--Ans: 000123

set @str = '1234'
select case when len(@str) < @minlen then REPLICATE('0',@minlen-len(@str))+@str else @str end
--Ans: 001234

set @str = '123456'
select case when len(@str) < @minlen then REPLICATE('0',@minlen-len(@str))+@str else @str end
--Ans: 123456

set @str = '123456789'
select case when len(@str) < @minlen then REPLICATE('0',@minlen-len(@str))+@str else @str end
--Ans: 123456789

set @str = '123456789'
select case when len(@str) < @minlen then REPLICATE('0',@minlen-len(@str))+@str else @str end
--Ans: 123456789


set @str = 'NEFT 123456789'
select case when len(@str) < @minlen then REPLICATE('0',@minlen-len(@str))+@str else @str end
--Ans: NEFT 123456789


0

ฉันสร้างฟังก์ชันเพื่อทำสิ่งนี้โดยที่คุณสามารถระบุความยาวอักขระเอาต์พุตที่ต้องการ:

CREATE FUNCTION [dbo].[udfLeadingZero]
(
        @String VARCHAR(MAX)
,       @Len INT
)
RETURNS VARCHAR(MAX)
BEGIN
    SET @String = RIGHT(REPLICATE('0',@Len)+@String,@Len)
RETURN @String
END
GO

ตัวอย่างผลลัพธ์


-5

วิธีที่มีประสิทธิภาพมากขึ้นคือ:

Select id, LEN(id)
From TableA
Order by 2,1 

The result :
id
----
1
2
12
123
1234

6
คำถามนี้ตอบคำถาม OP เกี่ยวกับการเติมด้วยศูนย์อย่างไร
Filburt
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.