foxty [العمل الأصلي]
مؤخرًا بدراسة كيفية كتابة خوارزمية ترحيل كبيرة وصغيرة، وقد قمت بفرزها وكانت الأفكار كما يلي:
أولاً، يجب أن يكون هناك حقل ترقيم تلقائي (ID) في قاعدة البيانات. ثم في الزيارة الأولى، قم بإخراج جميع السجلات، وتخصيص عدد السجلات في كل صفحة PageSize، وحساب عدد الصفحات، ثم قم بإنشاء مصفوفة PageId (PageCount) أحادية البعد بناءً على عدد الصفحات ) يحفظ شروط الاختبار الأولية للسجل، ثم يطابق كل عنصر، ويحفظ رمز حدود المعرف المقابل لكل صفحة (
1. كود حدود المعرف: إذا كان تسلسل سجل معرف سجل قاعدة البيانات كما يلي: 1، 2، 3، 4، 5، 6، 7، 8، 9، 10، 11، 12، 13، 14، 15، 16
بافتراض أنك بحاجة إلى الفرز حسب المعرف، PageSize = 5، Pagecount = 4، PageId(4)
قيم المصفوفة PageId هي PageId(0) = 1، PageId(1) = 5، PageId(2) = 10، PageId(3) = 15، PageId(4) = 16
عند الوصول إلى الصفحة i، ابحث مباشرة عن السجلات بين [PageId(i-1)، PageId(i)). وهذا يضمن استرداد سجلات PageSize فقط في كل مرة.
لنفترض أنك بحاجة إلى الفرز حسب المعرف بترتيب عكسي،
قيم مصفوفة PageId هي PageId(0) = 16، PageId(1) = 12، PageId(2) = 7، PageId(3) = 2، PageId(4) = 1. عند الوصول إلى i-th الصفحة، ابحث مباشرة عن المعرف الذي ينتمي إلى [ PageId(i-1) , PageId(i)) )
)
احفظ المصفوفة PageId() في Application() لسهولة الوصول إليها، بحيث تتم تهيئة Application() فقط في المرة الأولى التي يتم فيها الوصول إلى جهاز النداء. جزء الكود هو كما يلي: (يشار إليه فيما بعد بالبرنامج الجديد)
<%
Time1 = الموقت ()
ديم كون
تعيين Conn = Server.CreateObject("Adodb.Connection")
Conn.open "Driver={MicroSoft Access Driver (*.mdb)};Dbq="&Server.MapPath("db.mdb")
"www.downcodes.com."
تعتيم الصفحة، عدد الصفحات، معرف الصفحة، قائمة الصفحات
خافت روبية، Sql
خافت IsInit، ط
IsInit = False 'يتم استخدام العلامة لتحديد ما إذا كان التطبيق ("PageId") قد تمت تهيئة أم لا
PageList = 20 'قم بتعيين 20 جزءًا من البيانات ليتم عرضها في كل صفحة
تعيين Rs = Server.CreateObject("Adodb.Recordset")
Page = Request.QueryString("Page") 'لاحظ أنه يجب التحقق من نوع رقم الصفحة
إذا كان IsEmpty(Application("PageId")) ثم "إذا لم تتم تهيئة التطبيق("PageId") بعد، فقم بتهيئته أولاً
Response.Write("تطبيق Init!<br>")
Sql = "Select * From test Order By Id Desc" 'افترض أنه تم فرز هذا بترتيب عكسي حسب المعرف
Rs.open Sql,Conn,1,1 'احصل على كائن مجموعة السجلات
إذا لم يكن (Rs.Eof أو Rs.Bof) ثم
Rs.PageSize = PageList 'قم بتعيين عدد السجلات لكل صفحة
عدد الصفحات = Rs.PageCount
ReDim PageId(PageCounts) 'أعد تعريف مصفوفة PageId
For i = 0 To PageCounts 'ابدأ في تعيين القيم للمصفوفة PageId()
إذا Rs.eof ثم الخروج ل
PageId(i) = Rs("ID")
Rs.Move (قائمة الصفحات)
التالي
Rs.MoveLast
معرف الصفحة (عدد الصفحات) = Rs("ID")
التطبيق.قفل ()
التطبيق ("معرف الصفحة") = معرف الصفحة
التطبيق.فتح()
نهاية إذا
إغلاق
نهاية إذا
IdStart = Clng(Application("PageId")(Page-1))
IdEnd = Clng(Application("PageId")(Page))
Sql = "اختر * من الاختبار حيث المعرف<="&IdStart&" والمعرف>"&IdEnd&" "
Rs.open Sql، كون، 1،1
في حين لا روبية.eof
الاستجابة.كتابة(rs(0)&"--"&rs(1))
Rs.MoveNext
ويند
إغلاق
تعيين روبية = لا شيء
كون.إغلاق
SetConn=لا شيء
بالنسبة إلى i = 1 إلى Ubound(Application("PageId"))
Response.Write("<a href='Test1.asp?Page="&i&"'>"&i&"</a> ")
التالي
Time2 = الموقت ()
الاستجابة.الكتابة("<br>"&(Time2-Time1)*1000)
'Application.Contents.Remove("معرف الصفحة")
%>
رمز الترحيل التقليدي هو كما يلي: (يشار إليه فيما بعد بالبرنامج القديم)
<%
Time1 = الموقت ()
ديم كون
تعيين Conn = Server.CreateObject("Adodb.Connection")
Conn.open "Driver={MicroSoft Access Driver (*.mdb)};Dbq="&Server.MapPath("db.mdb")
تعتيم الصفحة، عدد الصفحات، قائمة الصفحات
خافت روبية، Sql
قائمة الصفحات = 20
الصفحة = Request.QueryString("الصفحة")
تعيين Rs = Server.CreateObject("Adodb.Recordset")
Sql = "اختر * من أمر الاختبار حسب وصف المعرف"
Rs.Open Sql، كون، 1،1
إذا كانت الصفحة = "" ثم الصفحة = 1
إذا لم يكن (Rs.eof أو Rs.Bof) ثم
Rs.PageSize = PageList
عدد الصفحات = Rs.PageCount
Rs.AbsolutePage = Page
نهاية إذا
لأني = 1 إلى قائمة الصفحات
إذا Rs.eof ثم الخروج ل
Response.Write(Rs(0)&"-----"&Rs(1)&"<br>")
Rs.MoveNext
التالي
لأني = 1 إلى عدد الصفحات
Response.Write("<a href='Test.asp?Page="&i&"'>"&i&"</a> ")
التالي
Time2 = الموقت ()
الاستجابة.الكتابة("<br>"&(Time2-Time1)*1000)
%>
في الواقع، الفكرة العامة هي إنشاء مصفوفة عامة من Application("PageId")، ويقوم كل عنصر بحفظ نطاق معرف السجل في الصفحة. على سبيل المثال، يحفظ Application("PageId")(0) معرف العنصر الأول. ثم يقوم التطبيق ("PageId") (1) بحفظ المعرف الأول للصفحة التالية... وهكذا عندما تحتاج إلى الوصول إلى الصفحة الأولى، ما عليك سوى البحث عن المعرف مباشرة في [Application(. "PageId")(i- 1) , Application("i") ) بهذه الطريقة، ما عليك سوى البحث في العدد المطلوب من السجلات في كل مرة، بدلاً من البحث في جميع السجلات في كل مرة الوصول الأول عندما يلزم إنشاء تطبيق المصفوفة ("PageId")، يكون أبطأ قليلاً عند الوصول إليه للمرة N (N> 1)، تكون السرعة أسرع بنحو 10 مرات امتحان:
1. هناك 32000 سجل في قاعدة البيانات، ويستغرق البرنامج القديم حوالي 500 مللي ثانية للوصول إلى صفحة واحدة، ويصل البرنامج الجديد إلى هذه المرة فقط أثناء الوصول الأول، ثم يستغرق حوالي 55 مللي ثانية فقط في كل مرة.
2. زيادة البيانات إلى 64000 سجل يستغرق البرنامج القديم حوالي 1000 مللي ثانية للوصول إلى صفحة واحدة ويصل البرنامج الجديد أيضًا إلى هذا المستوى عند الوصول إليه لأول مرة، ويظل عند حوالي 55 مللي ثانية في كل مرة بعد ذلك.
3. زيادة البيانات إلى 128000 سجل يستغرق البرنامج القديم حوالي 1900 مللي ثانية للوصول إلى صفحة واحدة، ويستغرق البرنامج الجديد حوالي 2300 مللي ثانية للوصول إلى صفحة واحدة لأول مرة، وبعد ذلك يستغرق كل وصول حوالي 70 مللي ثانية فقط.
ما يجب ملاحظته هنا هو أنه في كل مرة يتم فيها تعديل قاعدة البيانات، يجب إعادة تعيين التطبيق ("PageId")
تجربة البحث: (أولاً وقبل كل شيء، شكرًا لك Ye Zi (DVBBS) على تجربتك) حاول عدم استخدام برنامج الترحيل المدمج، Rs.RecordCount يستهلك الكثير من الموارد. في المقابل، من المقدر أن Rs.PageCount... يستهلك أيضًا الموارد، كما تم تحسين تأثير استخدام Rs.GetRows() بشكل ملحوظ.
بعد المقارنة، تكون سرعة وكفاءة الخوارزمية الورقية مرتفعة نسبيًا عندما تكون السجلات عالية نسبيًا. لكنها ليست مستقرة جدًا، وأحيانًا (نادرًا) تقفز من حوالي 30 مللي ثانية إلى 1-200 مللي ثانية. وبعد ذلك تنخفض الكفاءة بشكل ملحوظ إلى 50-80 مللي ثانية، وكلما تأخرت انخفضت الكفاءة. كفاءة الخوارزمية الجديدة منخفضة نسبيًا لأول مرة، حوالي 500 مللي ثانية، لكنها مستقرة نسبيًا لاحقًا، بشكل عام حوالي 50 مللي ثانية، ومع تغير عدد السجلات في المكتبة، تظل هذه السرعة كما هي. لن يتغير شيء. في المرة القادمة سأحاول دمج Ye Ye مع الخوارزمية الخاصة بي، لكن خوارزمية Ye Ye جيدة جدًا ومتعددة الاستخدامات. يمكنني استخدامه فقط للدردشة.