سؤال

ما هي أفضل طريقة لتخزين قائمة مرتبطة في قاعدة بيانات MySQL بحيث تكون الإدخالات بسيطة (أي؟ليس عليك إعادة فهرسة مجموعة من الأشياء في كل مرة) بحيث يمكن سحب القائمة بالترتيب بسهولة.

هل كانت مفيدة؟

المحلول

قم بتخزين عمود عدد صحيح في جدولك يسمى "الموضع".سجل 0 للعنصر الأول في قائمتك، و1 للعنصر الثاني، وما إلى ذلك.قم بفهرسة هذا العمود في قاعدة البيانات الخاصة بك، وعندما تريد سحب القيم الخاصة بك، قم بالفرز حسب هذا العمود.

 alter table linked_list add column position integer not null default 0;
 alter table linked_list add index position_index (position);
 select * from linked_list order by position;

لإدراج قيمة في الفهرس 3، قم بتعديل مواضع الصفوف 3 وما فوق، ثم قم بإدراج:

 update linked_list set position = position + 1 where position >= 3;
 insert into linked_list (my_value, position) values ("new value", 3); 

نصائح أخرى

باستخدام حل أدريان، ولكن بدلاً من الزيادة بمقدار 1، قم بزيادة بمقدار 10 أو حتى 100.ومن ثم يمكن حساب عمليات الإدراج بنصف الفرق بين ما تقوم بإدراجه دون الحاجة إلى تحديث كل شيء أسفل الإدراج.اختر رقمًا كبيرًا بما يكفي للتعامل مع متوسط ​​عدد عمليات الإدراج - إذا كان صغيرًا جدًا، فسيتعين عليك الرجوع إلى تحديث جميع الصفوف بموضع أعلى أثناء عملية الإدراج.

قم بإنشاء جدول يحتوي على عمودين مرجعيين ذاتيًا المعرف السابق والمعرف التالي.إذا كان العنصر هو أول شيء في القائمة، فسيكون المعرف السابق فارغًا، وإذا كان الأخير، فسيكون NextID خاليًا.سيبدو SQL شيئًا مثل هذا:

create table tblDummy
{
     PKColumn     int     not null, 
     PreviousID     int     null, 
     DataColumn1     varchar(50)     not null, 
     DataColumn2     varchar(50)     not null,  
     DataColumn3     varchar(50)     not null, 
     DataColumn4     varchar(50)     not null, 
     DataColumn5     varchar(50)     not null, 
     DataColumn6     varchar(50)     not null, 
     DataColumn7     varchar(50)     not null, 
     NextID     int     null
}

يمكن تخزين القائمة المرتبطة باستخدام مؤشرات متكررة في الجدول.هذا هو إلى حد كبير نفس التسلسلات الهرمية المخزنة في Sql وهذا يستخدم نمط الارتباط العودي.

يمكنك معرفة المزيد عنها هنا.

آمل أن يساعد هذا.

سيكون أبسط خيار هو إنشاء جدول يحتوي على صف لكل عنصر قائمة، وعمود لموضع العنصر، وأعمدة للبيانات الأخرى في العنصر.ثم يمكنك استخدام ORDER BY في عمود الموضع للاسترداد بالترتيب المطلوب.

create table linked_list
(   list_id   integer not null
,   position  integer not null 
,   data      varchar(100) not null
);
alter table linked_list add primary key ( list_id, position );

للتعامل مع القائمة، ما عليك سوى تحديث الموضع ثم إدراج/حذف السجلات حسب الحاجة.لذلك لإدراج عنصر في القائمة 1 في الفهرس 3:

begin transaction;

update linked_list set position = position + 1 where position >= 3 and list_id = 1;

insert into linked_list (list_id, position, data)
values (1, 3, "some data");

commit;

نظرًا لأن العمليات في القائمة يمكن أن تتطلب أوامر متعددة (على سبيل المثال، سيتطلب الإدخال إدراجًا وتحديثًا)، تأكد من تنفيذ الأوامر دائمًا ضمن المعاملة.

أحد أشكال هذا الخيار البسيط هو زيادة الموضع بعامل معين لكل عنصر، على سبيل المثال 100، بحيث عندما تقوم بإجراء INSERT، لا تحتاج دائمًا إلى إعادة ترقيم موضع العناصر التالية.ومع ذلك، يتطلب هذا المزيد من الجهد لمعرفة متى يجب زيادة العناصر التالية، لذلك تفقد البساطة ولكنك تكتسب الأداء إذا كان لديك العديد من الإدخالات.

اعتمادًا على متطلباتك، قد تروق لك خيارات أخرى، مثل:

  • إذا كنت تريد تنفيذ الكثير من المعالجات في القائمة وليس العديد من عمليات الاسترجاع، فقد تفضل أن يكون لديك عمود معرف يشير إلى العنصر التالي في القائمة، بدلاً من استخدام عمود الموضع.فأنت بحاجة إلى المنطق التكراري في استرجاع القائمة من أجل ترتيب العناصر.يمكن تنفيذ ذلك بسهولة نسبيًا في عملية مخزنة.

  • إذا كان لديك العديد من القوائم، فهناك طريقة سريعة لتسلسل قائمتك وإلغاء تسلسلها إلى نص/ثنائي، وتريد فقط تخزين القائمة بأكملها واستردادها، ثم قم بتخزين القائمة بأكملها كقيمة واحدة في عمود واحد.ربما ليس ما تطلبه هنا بالرغم من ذلك.

هذا المنشور قديم ولكنه لا يزال سيعطي .02 دولارًا.يبدو تحديث كل سجل في جدول أو مجموعة سجلات أمرًا مجنونًا لحل مشكلة الترتيب.كما أن حجم الفهرسة مجنون أيضًا، ولكن يبدو أن معظمهم قد قبلوه.

الحل المجنون الذي توصلت إليه لتقليل التحديثات والفهرسة هو إنشاء جدولين (وفي معظم حالات الاستخدام لا تقوم بفرز جميع السجلات في جدول واحد فقط على أي حال).الجدول A للاحتفاظ بسجلات القائمة التي يتم فرزها والجدول B للتجميع والاحتفاظ بسجل الترتيب كسلسلة.تمثل سلسلة الطلب مصفوفة يمكن استخدامها لترتيب السجلات المحددة إما على خادم الويب أو طبقة المتصفح لتطبيق صفحة الويب.

Create Table A{
Id int primary key identity(1,1),
Data varchar(10) not null
B_Id int
}

Create Table B{
Id int primary key Identity(1,1),
GroupName varchat(10) not null,
Order varchar(max) null
}

يجب أن يكون تنسيق أمر اللدغة هو المعرف والموضع وبعض الفواصل لتقسيم () السلسلة الخاصة بك.في حالة jQuery UI، تقوم الدالة .sortable('serialize') بإخراج سلسلة ترتيب لك تكون متوافقة مع POST والتي تتضمن معرف وموضع كل سجل في القائمة.

السحر الحقيقي هو الطريقة التي تختارها لإعادة ترتيب القائمة المحددة باستخدام سلسلة الترتيب المحفوظة.سيعتمد هذا على التطبيق الذي تقوم بإنشائه.إليك مثال مرة أخرى من jQuery لإعادة ترتيب قائمة العناصر: http://ovisdevelopment.com/oramincite/?p=155

https://dba.stackexchange.com/questions/46238/linked-list-in-sql-and-trees يقترح خدعة استخدام عمود موضع الفاصلة العائمة للإدراج والترتيب السريع.

ويذكر أيضًا SQL Server 2014 المتخصص التسلسل الهرمي ميزة.

هناك بعض الأساليب التي يمكنني التفكير فيها على الفور، ولكل منها مستويات مختلفة من التعقيد والمرونة.أفترض أن هدفك هو الحفاظ على الطلب قيد الاسترجاع، بدلاً من طلب التخزين كقائمة مرتبطة فعلية.

إن أبسط طريقة هي تعيين قيمة ترتيبية لكل سجل في الجدول (على سبيل المثال:1، 2، 3، ...).وبعد ذلك، عندما تقوم باسترداد السجلات، حدد ترتيبًا على العمود الترتيبي لإعادتها إلى ترتيبها مرة أخرى.

يتيح لك هذا الأسلوب أيضًا استرداد السجلات بغض النظر عن العضوية في القائمة، ولكنه يسمح بالعضوية في قائمة واحدة فقط، وقد يتطلب عمود "معرف القائمة" الإضافي للإشارة إلى القائمة التي ينتمي إليها السجل.

قد يكون النهج الأكثر تفصيلاً قليلاً، ولكن أيضًا أكثر مرونة، هو تخزين المعلومات حول العضوية في قائمة أو قوائم في جدول منفصل.سيحتاج الجدول إلى 3 أعمدة:معرف القائمة والقيمة الترتيبية ومؤشر المفتاح الخارجي لسجل البيانات.وبموجب هذا النهج، لا تعرف البيانات الأساسية شيئًا عن عضويتها في القوائم، ويمكن إدراجها بسهولة في قوائم متعددة.

أعتقد أنه من الأسهل إضافة عمود تم إنشاؤه من Datetime اكتب وعمود موضع int, ، حتى الآن يمكن أن يكون لديك مواضع مكررة، في عبارة التحديد استخدم order by الموضع، وخيار التنازلي الذي تم إنشاؤه وسيتم جلب قائمتك بالترتيب.

هذا شيء كنت أحاول اكتشافه بنفسي منذ فترة.أفضل طريقة وجدتها حتى الآن هي إنشاء جدول واحد للقائمة المرتبطة باستخدام التنسيق التالي (هذا رمز زائف):

قائمة مرتبطة(

  • مفتاح 1,
  • معلومة،
  • key2

)

key1 هي نقطة البداية.Key2 هو مفتاح خارجي يرتبط بنفسه في العمود التالي.لذا فإن أعمدتك ستربط شيئًا مثل هذا

العقيد 1

  • مفتاح 1 = 0،
  • المعلومات = "مرحبا"
  • المفتاح 2 = 1

Key1 هو المفتاح الأساسي لـ col1.key2 هو مفتاح خارجي يؤدي إلى المفتاح 1 الخاص بـ col2

col2

  • مفتاح 1 = 1،
  • المعلومات = 'wassup'
  • key2 = فارغ

تم تعيين key2 من col2 على قيمة خالية لأنها لا تشير إلى أي شيء

عند إدخال عمود في الجدول لأول مرة، ستحتاج إلى التأكد من تعيين key2 على القيمة null وإلا فسوف تحصل على خطأ.بعد إدخال العمود الثاني، يمكنك العودة وتعيين المفتاح 2 من العمود الأول إلى المفتاح الأساسي للعمود الثاني.

يعد هذا أفضل طريقة لإدخال العديد من الإدخالات في وقت واحد، ثم الرجوع وتعيين المفاتيح الخارجية وفقًا لذلك (أو إنشاء واجهة مستخدم رسومية تقوم بذلك نيابةً عنك)

إليك بعض التعليمات البرمجية الفعلية التي قمت بإعدادها (جميع التعليمات البرمجية الفعلية تعمل على MSSQL.قد ترغب في إجراء بعض الأبحاث حول إصدار SQL الذي تستخدمه!):

createtable.sql

create table linkedlist00 (

key1 int primary key not null identity(1,1),

info varchar(10),

key2 int

)

Register_foreign_key.sql

alter table dbo.linkedlist00

add foreign key (key2) references dbo.linkedlist00(key1)

*أضعهم في ملفين منفصلين، لأنه يجب أن يتم ذلك في خطوتين.لن يسمح لك MSSQL بالقيام بذلك في خطوة واحدة، لأن الجدول غير موجود بعد للرجوع إليه بالمفتاح الخارجي.

القائمة المرتبطة قوية بشكل خاص في واحد لكثير العلاقات.إذن، إذا كنت تريد إنشاء مجموعة من المفاتيح الخارجية؟حسنًا، هذه إحدى الطرق للقيام بذلك!يمكنك إنشاء جدول أساسي يشير إلى العمود الأول في جدول القائمة المرتبطة، ثم بدلاً من حقل "المعلومات"، يمكنك استخدام مفتاح خارجي لجدول المعلومات المطلوب.

مثال:

لنفترض أن لديك بيروقراطية تحافظ على النماذج.

لنفترض أن لديهم طاولة تسمى حافظة الملفات

حافظة الملفات(

  • معرف الخزانة (pk)
  • معرف الملفات (FK))

يحتوي كل عمود على مفتاح أساسي للخزانة ومفتاح خارجي للملفات.يمكن أن تكون هذه الملفات نماذج ضريبية، وأوراق التأمين الصحي، وقسائم أذونات الرحلات الميدانية وما إلى ذلك

الملفات(

  • معرف الملفات (pk)

  • معرف الملف (fk)

  • معرف الملف التالي (fk)

)

هذا بمثابة حاوية للملفات

ملف(

  • معرف الملف (pk)

  • معلومات عن الملف

)

هذا هو الملف المحدد

قد تكون هناك طرق أفضل للقيام بذلك، وهي موجودة، اعتمادًا على احتياجاتك الخاصة.يوضح المثال فقط الاستخدام المحتمل.

يمكن تخزين القائمة من خلال وجود عمود يحتوي على الإزاحة (موضع فهرس القائمة) - ثم يتم إدراج إدراج في المنتصف فوق الأصل الجديد ثم إجراء إدراج.

قم بزيادة "فهرس" SERIAL بمقدار 100، ولكن قم بإضافة القيم المتوسطة يدويًا بـ "فهرس" يساوي Prev+Next / 2.إذا قمت بإشباع الصفوف الـ 100، فأعد ترتيب الفهرس مرة أخرى إلى 100 ثانية.

يجب أن يحافظ هذا على التسلسل مع الفهرس الأساسي.

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top