PDA

View Full Version : مشكل با تاريخ شمسي



soroosh_i58
یک شنبه 17 آذر 1387, 08:50 صبح
من توي برنامم كه به زبان vb.net هست از fardate.dll استفاده كردم كه وقتي تاريخ شمسي رو بهش ميدي به تاريخ ميلادي تبديل ميكنه و از طريق توابع مربوط به تاريخهاي ميلادي تونستم اختلاف بين دو تاريخ شمسي رو اينجوري به دست بيارم. اما اين تكنيك براي به دست آوردن اختلاف 2 تاريخ مشخص مفيد هست ولي اگه بخوام توي بانك اطلاعاتيم كه 5000 تا ركورد داره تمام كساني كه تاريخ تولدشون مثلا بعد از 01/01/1370 هستند رو استخراج كنم به مشكل بر ميخورم چون منطقي نيست اين پردازشهارو روي تك تك ركوردها انجام بدم. ميخوام يه جوري از دستورات sql استفاده كنم. مثلا تي برنامم يك query بنويسم كه اينجوري باشه:
select * from table1
where columndate>#1370/01/01#
به نظر شما راهش چيه؟

AminSobati
یک شنبه 17 آذر 1387, 23:26 عصر
اگر تاریخ رو به صورت شمسی (کاراکتری) ذخیره کردین، عملگرهای بزرگتر-کوچکتر میتونن استفاده بشن. QUery که نوشتین اشکالش چیه؟ (ضمنا از Single Quote به جای Number Sign استفاده کنید)

ar.shirazi
دوشنبه 18 آذر 1387, 15:15 عصر
من توي برنامم كه به زبان vb.net هست از fardate.dll استفاده كردم كه وقتي تاريخ شمسي رو بهش ميدي به تاريخ ميلادي تبديل ميكنه و از طريق توابع مربوط به تاريخهاي ميلادي تونستم اختلاف بين دو تاريخ شمسي رو اينجوري به دست بيارم. اما اين تكنيك براي به دست آوردن اختلاف 2 تاريخ مشخص مفيد هست ولي اگه بخوام توي بانك اطلاعاتيم كه 5000 تا ركورد داره تمام كساني كه تاريخ تولدشون مثلا بعد از 01/01/1370 هستند رو استخراج كنم به مشكل بر ميخورم چون منطقي نيست اين پردازشهارو روي تك تك ركوردها انجام بدم. ميخوام يه جوري از دستورات sql استفاده كنم. مثلا تي برنامم يك query بنويسم كه اينجوري باشه:
select * from table1
where columndate>#1370/01/01#
به نظر شما راهش چيه؟
در این زمینه یک راه بسیار خوب این است که برای تاریخ، دو فیلد داشته باشید. یک فیلد از نوع کاراکتر برای تاریخ شمسی و یک فیلد از نوع datetime برای ذخیره تاریخ میلادی معادل آن
اعمال همچون جستجو، اعمال ریاضی (اضافه کردن، کم کردن، مقایسه و ...) را بر روی فیلد میلادی انجام دهید و اعمال همچون report را بر روی فیلد شمسی

Omid Rekabsaz
سه شنبه 19 آذر 1387, 20:24 عصر
پارامتر ورودی را به آنچه در پایگاه داده ذخیره شده تبدیل کنید و پس از فیلتر اطلاعات، اطلاعات را به کاربر نمایش دهید... مثلا اگر اطلاعات در پایگاه داده به میلادی ذخیره شده اند، و کاربر در رابط کاربری تاریخ را فارسی وارد می کند، پارامتر های ورودی کاربر را میلادی کنید و به پایگاه داده پاس کنید و دوباره خروجی را شمسی کنید...

ar.shirazi
چهارشنبه 20 آذر 1387, 07:25 صبح
پارامتر ورودی را به آنچه در پایگاه داده ذخیره شده تبدیل کنید و پس از فیلتر اطلاعات، اطلاعات را به کاربر نمایش دهید... مثلا اگر اطلاعات در پایگاه داده به میلادی ذخیره شده اند، و کاربر در رابط کاربری تاریخ را فارسی وارد می کند، پارامتر های ورودی کاربر را میلادی کنید و به پایگاه داده پاس کنید و دوباره خروجی را شمسی کنید...

این کار پسندیده و منطقی است. اما اگر بخواهیم از جدول ریپورت بگیریم و به کاربر نمایش دهیم، آنگاه به تعداد رکوردها باید تایع مبدل تاریخ میلادی به شمسی فراخوانی شود که زمان بر است.

soroosh_i58
چهارشنبه 20 آذر 1387, 18:47 عصر
درسته آقای ar.shrizari. خیلی خیلی سپاسگزارم .خودم هم به این نتیجه رسیدم که بهترین کار استفاده از دو فیلد هست. ای کاش همونطور که شرکت میکروسافت در دات نت امکان استفاده از تاریخ شمسی را گنجانده، همین کار رو برای sql هم انجام بده. به امید اون روز

ar.shirazi
چهارشنبه 20 آذر 1387, 20:51 عصر
درسته آقای ar.shrizari. خیلی خیلی سپاسگزارم .خودم هم به این نتیجه رسیدم که بهترین کار استفاده از دو فیلد هست. ای کاش همونطور که شرکت میکروسافت در دات نت امکان استفاده از تاریخ شمسی را گنجانده، همین کار رو برای sql هم انجام بده. به امید اون روز
خواهش میکنم
البته دلیل این که فیلد datetime شمسی رو ساپورت نمیکنه رو میدونین که؟

soroosh_i58
پنج شنبه 21 آذر 1387, 15:29 عصر
البته دلیل این که فیلد datetime شمسی رو ساپورت نمیکنه رو میدونین که؟
شاید به فکرشون نرسیده که برای sql هم مثل .net2005 همین کار رو بکنن. دلیل دیگه ای هم داره؟

ar.shirazi
پنج شنبه 21 آذر 1387, 17:32 عصر
شاید به فکرشون نرسیده که برای sql هم مثل .net2005 همین کار رو بکنن. دلیل دیگه ای هم داره؟

خیر قربان
فیلد datetime یک عدد 8 بایت است که 4 بایت آن تعداد روزهای گذشته از ژانویه 1753 را ذخیره میکند و 4 بایت دیگر تعداد میلی ثانیه هایی که از نیمه شب گذشته را

برای همین از سال 1753 به قبل قادر به ذخیره سازی نیست

soroosh_i58
پنج شنبه 21 آذر 1387, 22:20 عصر
چه جالب . ممنون از اطلاعات خوبتون.

linux
جمعه 22 آذر 1387, 04:26 صبح
این کار پسندیده و منطقی است. اما اگر بخواهیم از جدول ریپورت بگیریم و به کاربر نمایش دهیم، آنگاه به تعداد رکوردها باید تایع مبدل تاریخ میلادی به شمسی فراخوانی شود که زمان بر است.
اصلا هم زمان بر نیست، اگر از توابع مناسب استفاده کنید.

ar.shirazi
جمعه 22 آذر 1387, 09:56 صبح
اصلا هم زمان بر نیست، اگر از توابع مناسب استفاده کنید.
چرا دوست گرامی
زمان بر است. در ریپورتهای حجیم با تعداد رکورد بالا و در حالی که برای هر رکورد بخواهیم چند بار توابع را فراخوانی کنیم، مسلما زمان بر تر از زمانی است که به صورت مستقیم داده را خوانده و به خروجی بفرستیم

linux
دوشنبه 25 آذر 1387, 08:44 صبح
چرا دوست گرامی
زمان بر است. در ریپورتهای حجیم با تعداد رکورد بالا و در حالی که برای هر رکورد بخواهیم چند بار توابع را فراخوانی کنیم، مسلما زمان بر تر از زمانی است که به صورت مستقیم داده را خوانده و به خروجی بفرستیم
توابع شما اگر در sql سرور باشه، مشکلی نیست زمانی هم نمی گیرد

تولائی
دوشنبه 25 آذر 1387, 11:14 صبح
با سلام

در این زمینه یک راه بسیار خوب این است که برای تاریخ، دو فیلد داشته باشید. یک فیلد از نوع کاراکتر برای تاریخ شمسی و یک فیلد از نوع datetime برای ذخیره تاریخ میلادی معادل آن
اعمال همچون جستجو، اعمال ریاضی (اضافه کردن، کم کردن، مقایسه و ...) را بر روی فیلد میلادی انجام دهید و اعمال همچون report را بر روی فیلد شمسی

به این کاری که شما می‌گید انجام بدند می‌گن افزونگی اطلاعات و قویا تقبیح شده. عمده‌ی مسئله‌ش هم سر update کردن فیلید دوم هنگام تغییر فیلد اصلی‌ه.


این کار پسندیده و منطقی است. اما اگر بخواهیم از جدول ریپورت بگیریم و به کاربر نمایش دهیم، آنگاه به تعداد رکوردها باید تایع مبدل تاریخ میلادی به شمسی فراخوانی شود که زمان بر است.

برای این کار تو sql sever 2000 می‌تونید از Extended Stored Procedureها استفاده کنید که رسما پوست‌تون کندس. تو Sql server 2005 به بعد می‌تونید از User-defined Aggregateها استفاده کنید که من هنوز از این دومی استفاده نکردم. من تو sql server 2000 به همین روش گزارش گرفتم خیلی تو کارایی تاثیر نداره.

ar.shirazi
سه شنبه 26 آذر 1387, 07:14 صبح
با سلام


به این کاری که شما می‌گید انجام بدند می‌گن افزونگی اطلاعات و قویا تقبیح شده. عمده‌ی مسئله‌ش هم سر update کردن فیلید دوم هنگام تغییر فیلد اصلی‌ه.



برای این کار تو sql sever 2000 می‌تونید از Extended Stored Procedureها استفاده کنید که رسما پوست‌تون کندس. تو Sql server 2005 به بعد می‌تونید از User-defined Aggregateها استفاده کنید که من هنوز از این دومی استفاده نکردم. من تو sql server 2000 به همین روش گزارش گرفتم خیلی تو کارایی تاثیر نداره.
دوست گرامی

1- دیگر زمانی که افزونگی داده ها یک مساله بحرانی بود گذشته است. متاسفانه در دانشگاه ها هنوز به همان شیوه چندین سال گذشته تدریس میشود.

الان مهم ترین چیز پردازش سریع است و توصیه میشود در صورتی که افزونگی باعث کاهش پردازش ها شود ، از افزونگی دریغ نکنیم!

نمونه بسیار واضح آن:

اگر نگاهی به جداول Membership در asp.net بیاندازید میبینید که یک ستون برای ذخیره سازی نام کاربری و یک ستون هم برای ذخیره سازی نام کاربری به صورت lowercase در نظر گرفته شده است.

یعنی حتی برای تبدیل نام کاربری به صورت lowercase که کار بسیار ساده و پیش پا افتاده ای است هم حاظر شده اند در table ها یک ستون اضافه و افزونگی داشته باشند تا آن که بخواهند هنگام استفاده از توابع استفاده کنند و زمان اجرا داده ها را پردازش کنند.

linux
سه شنبه 26 آذر 1387, 08:20 صبح
دوست گرامی

1- دیگر زمانی که افزونگی داده ها یک مساله بحرانی بود گذشته است. متاسفانه در دانشگاه ها هنوز به همان شیوه چندین سال گذشته تدریس میشود.

الان مهم ترین چیز پردازش سریع است و توصیه میشود در صورتی که افزونگی باعث کاهش پردازش ها شود ، از افزونگی دریغ نکنیم!

نمونه بسیار واضح آن:

اگر نگاهی به جداول Membership در asp.net بیاندازید میبینید که یک ستون برای ذخیره سازی نام کاربری و یک ستون هم برای ذخیره سازی نام کاربری به صورت lowercase در نظر گرفته شده است.

یعنی حتی برای تبدیل نام کاربری به صورت lowercase که کار بسیار ساده و پیش پا افتاده ای است هم حاظر شده اند در table ها یک ستون اضافه و افزونگی داشته باشند تا آن که بخواهند هنگام استفاده از توابع استفاده کنند و زمان اجرا داده ها را پردازش کنند.

حاضر درست هست.
دلیل این کارشان هر چه باشد به خاطر سرعت در پردازش نیست چون اصلا اهمیتی ندارد.
شما هم بگردی قبلا کد برای تبدیل تقویم در همین بخش گذاشته شده ، می توانی استفاده کنی. حال مگر حجیم ترین جدول شما چقدر ممکن اطلاعات داشته باشه که اینقدر روی سرعت پردازش اصرار داری؟

تولائی
سه شنبه 26 آذر 1387, 09:05 صبح
دوست گرامی

1- دیگر زمانی که افزونگی داده ها یک مساله بحرانی بود گذشته است. متاسفانه در دانشگاه ها هنوز به همان شیوه چندین سال گذشته تدریس میشود.

الان مهم ترین چیز پردازش سریع است و توصیه میشود در صورتی که افزونگی باعث کاهش پردازش ها شود ، از افزونگی دریغ نکنیم!

نمونه بسیار واضح آن:

اگر نگاهی به جداول Membership در asp.net بیاندازید میبینید که یک ستون برای ذخیره سازی نام کاربری و یک ستون هم برای ذخیره سازی نام کاربری به صورت lowercase در نظر گرفته شده است.

یعنی حتی برای تبدیل نام کاربری به صورت lowercase که کار بسیار ساده و پیش پا افتاده ای است هم حاظر شده اند در table ها یک ستون اضافه و افزونگی داشته باشند تا آن که بخواهند هنگام استفاده از توابع استفاده کنند و زمان اجرا داده ها را پردازش کنند.

شاید مسئله افزونگی به لحاظ حجم داده الان اساسا اهمیت نداشته باشد ولی به این همیشه مشکل نگهداری را خواهد داشت. مسئله طراحی پایگاه داده مسئله‌ای جدا از پیاده‌سازی برنامه برای ورود داده به آن پایگاه داده است. ممکن است که تیم‌های مجزا برای ورود داده به پایگاه داده برنامه‌نویسی کنند( مثلا گروهی برای سیستم تحت وب و گروهی برای سیستم فرم‌بیس). کافی‌ست گروهی یکی از این افزونگی‌ها را در نظر نگیرد. صد در صد مشکل به وجود می‌آید. در ضمن دوست عزیز ماکروسافتمان کارهای با مزه زیاد می‌کند. این که یک نمونه از این کارهای را سند آورید لزوما قانع کننده نیست.

ar.shirazi
سه شنبه 26 آذر 1387, 23:14 عصر
شاید مسئله افزونگی به لحاظ حجم داده الان اساسا اهمیت نداشته باشد ولی به این همیشه مشکل نگهداری را خواهد داشت. مسئله طراحی پایگاه داده مسئله‌ای جدا از پیاده‌سازی برنامه برای ورود داده به آن پایگاه داده است. ممکن است که تیم‌های مجزا برای ورود داده به پایگاه داده برنامه‌نویسی کنند( مثلا گروهی برای سیستم تحت وب و گروهی برای سیستم فرم‌بیس). کافی‌ست گروهی یکی از این افزونگی‌ها را در نظر نگیرد. صد در صد مشکل به وجود می‌آید. در ضمن دوست عزیز ماکروسافتمان کارهای با مزه زیاد می‌کند. این که یک نمونه از این کارهای را سند آورید لزوما قانع کننده نیست.

دوست گرامی:
نخست این که منظور از این جمله را متوجه نشدم:

ولی به این همیشه مشکل نگهداری را خواهد داشت.

دیگر این که در خصوص تیم های محزا فرمودید:

ممکن است که تیم‌های مجزا برای ورود داده به پایگاه داده برنامه‌نویسی کنند( مثلا گروهی برای سیستم تحت وب و گروهی برای سیستم فرم‌بیس). کافی‌ست گروهی یکی از این افزونگی‌ها را در نظر نگیرد. صد در صد مشکل به وجود می‌آید.

چگونه ممکن است تیمی برای سیستم برنامه نویسی کند که با آن آشنایی ندارد؟


در ضمن دوست عزیز ماکروسافتمان کارهای با مزه زیاد می‌کند. این که یک نمونه از این کارهای را سند آورید لزوما قانع کننده نیست

خیر، این کار با مزه نیست. کارشناسی شده، دقیق و با دلیل است. مسلما شرکتی که خودش Sql server را بعنوان یکی از قویترین پایگاه داده های دنیا طراحی کرده است از آن اطلاعات بیشتری دارد و طراحی که بر مبنای آن انجام میدهد دقیق تر است.

دلیل آوردن این مثال هم این بود که عرض کنم افزایش افزونگی به شرط کاهش پردازش مشکلی ندارد.
در دیگر برنامه ها هم مثالهایی از این دست زیاد است.

تولائی
سه شنبه 03 دی 1387, 08:43 صبح
با سلام مجدد


دیگر این که در خصوص تیم های محزا فرمودید:

«ولی به این همیشه مشکل نگهداری را خواهد داشت. »


با ایرادی که گرفتید کاملا موافقم. دو کلمه «به این» اضافه بود. پس اصلاح شده جمله فوقم می‌شود
«ولی همیشه مشکل نگهداری را خواهد داشت. »



چگونه ممکن است تیمی برای سیستم برنامه نویسی کند که با آن آشنایی ندارد؟

این مطلب هم کاملا ممکن است. واضح است که شرکتی نخواهد نیرو ارزشمند و گران‌قیمت طراحش را نخواهد به کار توسعه سیستم بگمارد. یا حتی طراح پایگاه داده به زبان برنامه‌نویسی تیم توسعه تسلط کافی نداشته باشد. در ضمن دقت کن لزومی ندارد که تیم توسعه‌ی برنامه بتواند که دخل و تصرفی در کار طراحی پایگاه داده داشته باشد.




افزایش افزونگی به شرط کاهش پردازش مشکلی ندارد.
در دیگر برنامه ها هم مثالهایی از این دست زیاد است.
این هم در نوع خود مسئله‌ایست. اگر پایگاه داده‌ات قرار نباشد که تغییر خواصی بکند و مسئله مسئله‌ی گزارش‌گیری است افزونگی احتمالا مشکل‌ساز نیست (مانند پایگاه داده اعلام نتایج کنکور). ولی اگر تغییرات پایگاه داده به اندازه‌ی کافی زیاد است افزونگی احتمالا مشکل‌ساز خواهد بود. غرض این‌که ایجاد افزونگی باید با احتیاط کامل باشد.

ar.shirazi
سه شنبه 03 دی 1387, 12:16 عصر
غرض این‌که ایجاد افزونگی باید با احتیاط کامل باشد.

آفرین، دقیقا.

Tooraj Farsi
سه شنبه 01 بهمن 1387, 14:57 عصر
سلام

فقط جهت اطلاع دوستان عرض میکنم ، ما برای فیلد تاریخ شمسی از نوع Int استفاده میکنیم. مثلاً برای تاریخ 87/07/12 از عدد 13870712 استفاده میکنیم. البته در نظر بگیرید که پایگاه داده IBM DB2 و جداول شامل تعداد رکورد بالاتر از 600 میلیون رکورد هستند.

دلایل استفاده از نوع Int

1 - محاسبه و پردازش سریعتر در اعداد
2 - پایین آمدن حجم فایل ایندکس

موفق باشید.

linux
سه شنبه 01 بهمن 1387, 16:54 عصر
من توي برنامم كه به زبان vb.net هست از fardate.dll استفاده كردم كه وقتي تاريخ شمسي رو بهش ميدي به تاريخ ميلادي تبديل ميكنه و از طريق توابع مربوط به تاريخهاي ميلادي تونستم اختلاف بين دو تاريخ شمسي رو اينجوري به دست بيارم. اما اين تكنيك براي به دست آوردن اختلاف 2 تاريخ مشخص مفيد هست ولي اگه بخوام توي بانك اطلاعاتيم كه 5000 تا ركورد داره تمام كساني كه تاريخ تولدشون مثلا بعد از 01/01/1370 هستند رو استخراج كنم به مشكل بر ميخورم چون منطقي نيست اين پردازشهارو روي تك تك ركوردها انجام بدم. ميخوام يه جوري از دستورات sql استفاده كنم. مثلا تي برنامم يك query بنويسم كه اينجوري باشه:
select * from table1
where columndate>#1370/01/01#
به نظر شما راهش چيه؟

می تونی این dll را به دیتابیس اضافه کنی و توابعی توی sql server با این dll بنویسی که کارت را راه بندازه

slashslash2009
سه شنبه 01 بهمن 1387, 17:23 عصر
منم این مشکلو داشتم ولی بعدش فیلدمو به نوع رشته ای تغییر دادم واسه اینکه فرقی نمیکنه حتی select کردن بین مثلا یه تاریخ تا تاریخ دیگه ای رو هم انجام میده