تبدیل تاریخ شمسی به میلادی–میلادی به شمسی– میلادی به قمری در Sql Server 2005-2008R2-2012
با کمی جستجو در اینترنت مشاهده خواهید کرد که توابع زیادی برای تبدیل تاریخ وجود دارد اما برخی از آنها یا کامل نیستند و یا اشکالاتی دارند. در این پست توابع تبدیل تاریخ شمسی به میلادی، میلادی به شمسی و میلادی به قمری را در کنار هم قرار دادهام. در نهایت نیز یک تابع جهت بدست آوردن سن افراد از تاریخ تولدشان معرفی شده است.
لازم به ذکر است که تابع تبدیل تاریخ میلادی به شمسی توسط آقای رضا راد نوشته شده است.
تابع تبدیل تاریخ میلادی به شمسی
Create FUNCTION [dbo].[GregorianToPersian] ( @Date varchar(10) ) RETURNS varchar(10) AS BEGIN DECLARE @ResultVar varchar(10) declare @Year int set @Year=convert(int,substring(@Date,1,4)) if(dbo.IsLeapYear(@Year)=1) if(@GregorianDayIndex>=80) declare @mdays int set @mdays=dbo.NumberOfDayInMonthPersian(@Year,@m) if(@index<=@mdays) set @ResultVar= — Return the result of the function END Create FUNCTION [dbo].[IsLeapYear] if @Year % 400 = 0 RETURN @ResultVar END Create FUNCTION [dbo].[NumberOfDayInMonthPersian] DECLARE @ResultVar int RETURN @ResultVar END Create FUNCTION [dbo].[NumberOfDaysInMonthGregorian] DECLARE @ResultVar int RETURN @ResultVar END |
تابع تبدیل تاریخ شمسی به میلادی
Create FUNCTION [dbo].[ShamsitoMiladi](@DateStr varchar(10)) RETURNS DATE AS BEGIN declare @YYear int,@MMonth int,@DDay int,@epbase int,@epyear int,@mdays int,@persian_jdn int,@i int, @j int,@l int,@n int,@TMPRESULT varchar(10),@IsValideDate int,@TempStr varchar(20),@TmpDateStr varchar(10) SET @i=charindex(‘/’,@DateStr) IF LEN(@DateStr) – CHARINDEX(‘/’, @DateStr,CHARINDEX(‘/’, @DateStr,1)+1) = 4 BEGIN IF ( ISDATE(@TmpDateStr) =1 ) RETURN @TmpDateStr ELSE RETURN NULL END ELSE SET @TmpDateStr = @DateStr IF ((@i<>0) and (ISNUMERIC(REPLACE(@TmpDateStr,‘/’,”))=1) and (charindex(‘.’,@TmpDateStr)=0)) BEGIN SET @YYear=CAST(SUBSTRING(@TmpDateStr,1,@i–1) AS INT) IF ( @YYear< 1300 ) SET @YYear =@YYear + 1300 IF @YYear > 9999 RETURN NULL SET @TempStr= SUBSTRING(@TmpDateStr,@i+1,Len(@TmpDateStr)) SET @i=charindex(‘/’,@TempStr) SET @MMonth=CAST(SUBSTRING(@TempStr,1,@i–1) AS INT) SET @MMonth=@MMonth— -1 SET @TempStr= SUBSTRING(@TempStr,@i+1,Len(@TempStr)) SET @DDay=CAST(@TempStr AS INT) SET @DDay=@DDay— – 1 IF ( @YYear >= 0 ) SET @epbase = @YYear – 474 Else SET @epbase = @YYear – 473 SET @epyear = 474 + (@epbase % 2820) IF (@MMonth <= 7 ) SET @mdays = ((@MMonth) – 1) * 31 Else SET @mdays = ((@MMonth) – 1) * 30 + 6 SET @persian_jdn =(@DDay) + @mdays + CAST((((@epyear * 682) – 110) / 2816) as int) + (@epyear – 1) * 365 + CAST((@epbase / 2820) as int ) * 1029983 + (1948321 – 1) IF (@persian_jdn > 2299160) BEGIN SET @l = @persian_jdn + 68569 SET @n = CAST(((4 * @l) / 146097) as int) SET @l = @l – CAST(((146097 * @n + 3) / 4) as int) SET @i = CAST(((4000 * (@l + 1)) / 1461001) as int) SET @l = @l – CAST( ((1461 * @i) / 4) as int) + 31 SET @j = CAST(((80 * @l) / 2447) as int) SET @DDay = @l – CAST( ((2447 * @j) / 80) as int) SET @l = CAST((@j / 11) as int) SET @MMonth = @j + 2 – 12 * @l SET @YYear = 100 * (@n – 49) + @i + @l END SET @TMPRESULT=Cast(@MMonth as varchar(2))+‘/’+CAST(@DDay Varchar(2))+‘/’+CAST(@YYear as varchar(4)) RETURN Cast(@TMPRESULT as varchar(10)) END RETURN NULL END |
از کوئری زیر برای مشاهده نتیجه استفاده کنید.
select dbo.GregorianToPersian(‘1980/01/01’)
select dbo.ShamsitoMiladi(‘1358/10/11’)
تبدیل تاریخ میلادی به قمری
از دستور زیر برای تبدلی تاریخ میلادی به قمری استفاده کنید.
SELECT CONVERT (nvarchar(30),GETDATE(),130) as Date
برای بدست آوردن سن از دستور زیر استفاده کنید.
SELECT DateDiff(yy , (select dbo.ShamsitoMiladi (‘1365/01/01‘) ), GetDate())
با عرض سلام و خسته نباشی.
مقدار متغیر @StartDayGregorianDateInPersianCalendar بجای 12 و 11 باید 22 و 21 باشه وگرنه برای تاریخ های 22 ماه 12 میلادی تا 30 ماه 12 میلادی خطا دار میشه. البته بسته به اینکه سال کبیسه باشه یا نه میتونه برای تاریخ های 21 ماه 12 میلادی تا 30 ماه 12 میلادی خطادار باشه.
با تشکر.
سلام.
به اشتباه گفته بودم که برای درست شدن تاریخ از 22 ماه 12 تا آخرش باید مقدار @StartDayGregorianDateInPersianCalendar از 11 و 12 به 21 و 22 تغییر بدین.
احتیاج نیست به اونها دست بزنید و شرمنده از اینکه لدون دقت این رو گفتم.
تنها یه تغییر کوچیک لازمه بدین تا این قضیه درست بشه اونهم اینه که توی فانکشن GregorianToPersian
این خط رو
if(@m=@StartMonthGregorianDateInPersianCalendar)
به این خط تغییر بدین
if(@m=@StartMonthGregorianDateInPersianCalendar) and @Month=1
با تشکر و معذرت از اشتباه قبلی