View Full Version : تغییر طراحی پایگاه داده با 5.000.000 رکورد ، برای افزایش سرعت در وب
asadi.hasan
سه شنبه 20 فروردین 1392, 11:55 صبح
سلام ، خسته نباشید؛
من یه جدولی دارم که جدول اعضا هستش .
و یک جدول دیگه دارم که ، شهرهایی که هر یک از اعضا انتخاب می کنند رو در اون به این صورت ذخیره می کنم:
هر کاربر برای خودش ، 10شهر رو انتخاب می کنه .
و هریک از این شهرها ، در جدول دوم ، با کد کاربری اون کاربر در یک رکورد ذخیره می شوند.
یعنی :نام شهر ، کد کاربر ،فیلدهای جدول دوم هستن.
واگر کاربری 10 شهر رو انتخاب کنه ، برای اون کاربر ، در جدول دوم ، 10 رکورد ذخیره میشه .
و اگر تعداد کاربرهام به یک میلیون برسه ، و هر کاربر ، میانگین ، 5 تا شهر داشته باشه ، تعداد رکورد هام در جدول دوم به 5.000.000 رکورد میرسه ، حالا اگه یه موقع ، کاربری بخواد ، شهرهای خودش رو ببینه ، من باید 5 میلیون رکورد رو سرچ کنم .
فکر نمیکنم این کار ، در وب ، کار درستی باشه !!!!
سوال : نظر شما برای رفع این مشکل چیه ؟
هر نظری که درباره ی تغییر طراحی پایگاه ،سرعت ،دارید بگید .البته مفید باشه .
ممنون از توجه شما دوست عزیز .
حمیدرضاصادقیان
سه شنبه 20 فروردین 1392, 22:13 عصر
سلام
ایا برای شهرهانیز یک جدول دارید؟
اگر اینطوریه که به جای نام شهر در جدول دوم ، کد شهر رو ذخیره کنید.
اگر ندارید پس ایجاد کنید.
درمورد رکوردها که فرمودین این تعداد اصلا رقمی نیست که نگران باشید.
اگر Index های مناسب روی جدول بذارید مشلی نخواهید داشت.
همچنین وقتی دارید داده ها رو واکشی میکنید ، فقط مثلا میخواهید یک کاربر رو ببینید که با توجه به Index های مناسب ، نیازی به Table Scan نیست و خیلی سریع به جواب مورد نظر میرسید.
tooraj_azizi_1035
چهارشنبه 21 فروردین 1392, 13:54 عصر
سلام
اگر در جدول شهر فقط شهر و کد کاربر ذخیره میشه (البته باید یک فیلد از نوع IDENTITY هم بگیرید که با اون بتونید هر رکورد رو از بقیه تفکیک کنید) کار درستی انجام دادید اما اگر اطلاعات شهر بیش از یک فیلد هست مثلاً استانی که شهر در اون هست کار درستی نیست و باید شهر رو یک جدول جدا بگیرید.
وقتی کوئری تون رو اجرا می کنید خود SQL Server قابلیت Missing Indexes داره که بهتون میگه فقدان وجود یک اندیس روی فلان ستون Performance Impact یا ضربه به کارایی کوئری رو در پی داشته.
این پیام با رنگ سبز وقتی شما دکمه Actual Execution Plan رو فعال می کنید در بالای پلن اجرایی نمایش داده میشه.
کوئری تون و عکسی از جداولتون رو بذارید تا پاسخ بهتری بگیرید.
حمیدرضاصادقیان
چهارشنبه 21 فروردین 1392, 21:46 عصر
اگر در جدول شهر فقط شهر و کد کاربر ذخیره میشه (البته باید یک فیلد از نوع IDENTITY هم بگیرید که با اون بتونید هر رکورد رو از بقیه تفکیک کنید) کار درستی انجام دادید
اتفاقا اصلا کار درستی انجام ندادند و قوانین نرمال سازی رو رعایت نکردند.
چون برای هر فرد میخوان مثلا ده تا شهر تعریف کنند.
ممکنه دو کاربر مختلف شهرهای یکسان داشته باشند.در اینجا اگر بخواهید نام شهر رو عوض کنید باید کل اسامی رو Update کنید. همچنین اگر یک کاربر فقط به یک شهر خاص ربط داده بشه و اون کاربر حذف بشه اون شهر نیز مشخصاتش حذف میشه . پس بهتره یک جدول ایجاد کننند که شامل کد شهر و نام شهر باشه و کد اونو به هر کاربر اختصاص بدهند.
asadi.hasan
پنج شنبه 22 فروردین 1392, 17:23 عصر
اگر Index های مناسب روی جدول بذارید مشلی نخواهید داشت.
یعنی چی که ایندکس هی مناسب روی جدول بزاریم ؟
اتفاقا اصلا کار درستی انجام ندادند و قوانین نرمال سازی رو رعایت نکردند.
چون برای هر فرد میخوان مثلا ده تا شهر تعریف کنند.
ممکنه دو کاربر مختلف شهرهای یکسان داشته باشند.در اینجا اگر بخواهید نام شهر رو عوض کنید باید کل اسامی رو Update کنید. همچنین اگر یک کاربر فقط به یک شهر خاص ربط داده بشه و اون کاربر حذف بشه اون شهر نیز مشخصاتش حذف میشه . پس بهتره یک جدول ایجاد کننند که شامل کد شهر و نام شهر باشه و کد اونو به هر کاربر اختصاص بدهند.
من دقیقا برای شهرستان هام یک جدول ایجاد کردم و کد شهرستان ها ، در جدولی که شهر ها را وارد می کنم ، به عنوان کلید خارجی است . بنابراین زمانی که دو کاربر ،شهرهای یکسان داشته باشند ،هیچ مشکلی پیش نمیاد.
من فقط از بالا بودن هزینه جستجو می ترسم .
مثلا اگه یه کاربر بخواد در پروفایلش، شهرهایی که انتخاب کرده رو ببینه ، کل رکورد هایی که در جدول شهرها(جدول دوم) هست ، باید واکشی بشه .
راه حل دیگه :
اما من خودم یک راه حل دیگه دارم :
جدول دوم که جدول شهرها هست رو به این فیلدها تغییر بدم :
یک فیلد "کد " داشته باشم و به ازای هر شهرستان ،یک فیلد داشته باشم . مثلااگه 200 شهرستان داشته باشیم ، تعداد فیلدهای من میشه 201 .
که به ازای هر کاربر ، یک رکورد ایجاد کنم و هر کاربر ، هر شهری رو که انتخاب کرد ، مقدار شهرهایی رو که انتخاب کرده ، با یک مقداری پر کنم که مشخص کنه این شهرها انتخاب شده .مثلا:
102651
این طوری در بهترین حالت ، فقط یک رکورد بررسی میشه و فقط در بدترین حالت ،کل رکوردها بررسی می شوند.
نظرتون چیه ؟این روش خوبه یا قبلی؟
ممنون ار توجهتون.
حمیدرضاصادقیان
پنج شنبه 22 فروردین 1392, 17:52 عصر
دوست عزیز نیازی نیست شما نگران واکشی اطلاعات باشید.
مثلا اگه یه کاربر بخواد در پروفایلش، شهرهایی که انتخاب کرده رو ببینه ، کل رکورد هایی که در جدول شهرها(جدول دوم) هست ، باید واکشی بشه .
به هیچ وجه یک همچین اتفاقی نمیافته اونم به خاطر نوع پردازش دستورات توسط SQL Server هست. یعنی درواقع فقط همون رکوردهایی رو برای شما واکشی میکنه که شما فیلتر کردید.
به جز این یکی از راههای تشخیص ایندکس مناسب این هست که مثلا دستور واکشی شهرها برای یک کاربر رو بنویسید و Execution Plan اونو بررسی کنید اینجوری خیلی راحی میشه ایندکسهای مناسب
گذاشت.
مثلا یک راهش این هست که شما روی فیلدهایی که در شرط قرار دارند لیندکس بذارید و فیلدهایی که جلوی عبارت Select نوشته شدند به صورت Include درون ایندکس قرار بگیرند.
پیشنهاد میکنم فصل اول کتاب Inside T-SQL Querying برای آقای Itzik Ben Gan رو حتما مطالعه کنید.
tooraj_azizi_1035
پنج شنبه 22 فروردین 1392, 20:18 عصر
اتفاقا اصلا کار درستی انجام ندادند و قوانین نرمال سازی رو رعایت نکردند.
چون برای هر فرد میخوان مثلا ده تا شهر تعریف کنند.
ممکنه دو کاربر مختلف شهرهای یکسان داشته باشند.در اینجا اگر بخواهید نام شهر رو عوض کنید باید کل اسامی رو Update کنید.
شهری مثل تهران پس از سالها از "طهران" به "تهران" تغییر نام پیدا کرد.
از ابتدا نگفتند که شهرستانی هم در کار هست تا بگیم جدول جدا بگیرند.
linux
پنج شنبه 22 فروردین 1392, 23:04 عصر
یک جدول شهرها دارید،( میتونید خیلی شیک جدول را بصورت خود ارجاع در نظر بگیرید که شهرستانها را هم به آن اضافه کنید)و یک جدول کاربران خوب این دوتا با هم ارتباط n-n دارند لازم دارید یک جدول دیگر هم داشته باشید که کد کاربر و کد شهر را در خودش نگهدارد. همین.
حمیدرضاصادقیان
جمعه 23 فروردین 1392, 01:10 صبح
شهری مثل تهران پس از سالها از "طهران" به "تهران" تغییر نام پیدا کرد.
لزومی نداره حتما اسم شهری عوض بشه.
مهم اینه که قوانین نرمال سازی رو از بین میبره.
ما بگیم چون مثلا اسم عوض نمیشه میتونن قوانین رو نقض کنند؟؟
asadi.hasan
جمعه 23 فروردین 1392, 20:27 عصر
مگه Sql Server چطوری جستجو میکنه ؟
بالاخره ، برای پیدا کردن یک رکورد ،باید ، کل رکورد ها رو با مقدار ، شرطی که در کوئری نوشته ایم مورد مقایسه قرار بده و هر رکوردی که برابر بود رو واکشی کنه . حالا چه ایندکس گذاری شده باشه یا هر چیز دیگه !!!
شاید نظر شما اینه که ، جستجوی 5.000.000 رکورد ،برای کامپیوترهای امروزی چیزی نیست و به همین دلیل میگید مشکلی پیش نمیاد .
اما من میخوام بهینه ترین راه رو برم .
پیشنهاد میکنم فصل اول کتاب Inside T-SQL Querying برای آقای Itzik Ben Gan رو حتما مطالعه کنید.
میشه لینکش رو قرار بدید ؟من یکی دو جا رفتم ، اما پولی بود.
حمیدرضاصادقیان
جمعه 23 فروردین 1392, 22:31 عصر
نه دوست عزیز ، به این شکل که شما فرمودین جستجو نمیکنه.اگر اینجوری جستجو میکرد که پس تفاوت جدول با Index و بدون Index در چی هست؟؟
این (http://msdn.microsoft.com/en-us/library/ms177443(v=sql.105).aspx) و این (http://msdn.microsoft.com/en-us/library/ms177484(v=sql.105).aspx) رو حتما یک نگاهی بکنید
vBulletin® v4.2.5, Copyright ©2000-1404, Jelsoft Enterprises Ltd.