هل يمكنني استخدام خوارزمية diff diff confortext لتتبع تغييرات XML؟

StackOverflow https://stackoverflow.com/questions/2430083

  •  19-09-2019
  •  | 
  •  

سؤال

أنا أعمل في Flex / AS3 ON (للبساطة) محرر XML. أحتاج إلى توفير وظيفة التراجع / الإعادة.

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


سؤالي هو - هل يمكنني استخدام خوارزمية Diffe Differytext لتتبع تغييرات XML هذه؟

أبحاثي على شبكة الإنترنت يشير إلى أنني لا تستطيع القيام بذلك. ومع ذلك، من الواضح أنني فقدت شيئا. يوفر Differext Diff وظيفة مزعومة:

diff(text, text') -> diffs
patch(text, diffs) -> text'

XML هو مجرد نص، فلماذا لا يمكنني فقط استخدام Diff () والتصحيح () لتحويل النص بشكل موثوق؟

على سبيل المثال: دعنا نقول أنني شاعر. عندما أكتب الشعر، استخدم الكثير من علامات الترقيم غير تقليدي ... كما تعلمون، مثل <، /، و>. (قد ترى أين أذهب مع هذا ...) إذا كنت أكتب شعري في تطبيق يستخدم DiFFS لتوفير وظيفة التراجع / الإعادة، فهل تصبح شعري مشوهة عندما قمت بالتراجع / إعادة تعديلاتي؟ انها مجرد نص! لماذا تحدث فرقا في الخوارزمية؟

من الواضح أنني لا أحصل على شيء هنا ... شكرا على شرح! :)

تحديث:

بعض النقاش الذي واجهته فيما يتعلق بفتحة XML مع خوارزمية نصية:


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

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

المحلول

أنا مؤلف مكتبة الفرق / المباراة / التصحيح العادي من Google.

السؤال الرئيسي هو ما إذا كانت بقعك دقيقة. في عالم مثالي:

  diff(old_text, new_text) -> edits
  patch(edits, old_text) -> new_text

لاحظ أن النص الأساسي (Old_Text) هو نفسه في كلتا العمليات. في هذه الحالة المثالية، ثم سيعمل فرق النص العادي البسيط والتصحيح بشكل مثالي، بغض النظر عن نوع المحتوى. إذا كانت هذه الحالة تنطبق عليك، فأنت تنتهي.

القضية تكمن مع الترقيع غامض. إليك المثال المقابل:

  diff(old_text, new_text) -> edits
  patch(edits, old_forked_text) -> new_forked_text

لاحظ أن النص الأساسي ليس هو نفسه في كلتا العمليات. يجب أن تكون متشابهة، لكن عملية التصحيح لديها الآن لاستخدام "الحكم" حول ما يجب القيام به. قد تناسب بعض التصحيحات تماما كما هو محدد في التعديل، قد يحتاج البعض الآخر إلى تعديلها للموقف، قد يحتاج الآخرون إلى تعديل سياق تغيير، قد لا يصلح الآخرون على الإطلاق ويجب إسقاطها. إذا لم يكن خوارزمية التصحيح الخاصة بك على دراية بنية XML عند اتخاذ قراراتها، فقد ينتهي بك جيدا مع XML Malfromed. إليك عينة:

  old_text = Jabberwock<SPAN>Hello<SPAN>World</SPAN></SPAN>
  new_text = Jabberwock<DIV>Hello<SPAN>World</SPAN></DIV>
  diff(old_text, new_text) -> edits
  edits = ["SPAN" -> "DIV" @ character 11,
           "SPAN" -> "DIV" @ character 41]
  old_forked_text = <SPAN>Hello<SPAN>World</SPAN></SPAN>
  patch(edits, old_forked_text) -> new_forked_text
  new_forked_text = <SPAN>Hello<DIV>World</SPAN></DIV>

دعونا ننظر إلى هذا بعناية. عاد فرق الأصلي اثنين من التعديلات، وتغيير فترة الأبعد إلى DIV. تغيير بسيط. لسوء الحظ، يتم تطبيق النص هذا التحرير الذي تم تغييره من الأصلي. تمت إزالة كلمة "Jabberwock". الآن يطابق تغيير الحف الأول الأول مع علامة الفترة الثانية، وليس أول واحد. نظرا لأن خوارزمية التصحيح ليست على دراية بقواعد XML، فإنها تؤدي إلى علامات متداخلة بشكل غير قانوني.

هناك بعض الاختراقات التي تسمح لك بضمان XML ساري المفعول عند استخدام تصحيح نص عادي، لكنها تؤدي إلى بعض فقدان المرونة (السؤال الأصلي يحتوي بالفعل على رابط إلى صفحة Wiki التي كتبت عنها. الحل النهائي للتصحيح XML هو بالطبع لاستخدام خوارزمية Diff واضحة XML. هذه أكثر تعقيدا ومكلفة للغاية، لكنها موجودة. Google أسماء Tancred Lindhedlm و Sebastian Rönnau للعمل الكبير الذي قاموا به في حقل XML (خاصة فيما يتعلق ب Doceng).

اسمحوا لي أن أعرف إذا كان هناك أي شيء آخر يمكنني إضافته.

- نيل فريزر

نصائح أخرى

أنا أستعمل بعد مقارنة في كل وقت لمقارنة مستندات XML. يفهم XML، إلى حد معين.

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

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

إذا كنت "المالك" الوحيد للبيانات بين نقاط التراجع / الإعادة بعد ذلك بالطبع يمكنك استخدام فرق منصبها. كما تشير، فإنه يصل إلى مجموعة من التحولات.

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

في السياق الأوسع، إذا سمحت بالتحرير الخارجي من هذه المستندات، وأنت تفكر في كيفية تخزين Deltas على الخادم، فأنت تقليد أنظمة تحكم GIT أو غيرها من أنظمة التحكم الأخرى. يجب عليك استخدام نوع من خوارزمية Diff لأن مجرد تسجيل الأوامر الخاصة بك من الواضح أنه ليس المصدر الوحيد للتحول. عند هذه النقطة، بدأت في خلط التراجع / الإعادة مع عنصر تحكم الإصدار وقد ترغب في التفكير بشدة في مربكة تلك المفاهيم للمستخدمين.

أود أن أظل التراجع / الإعادة كما ضمن جلسة التحرير وحظر التحرير الخارجي أثناء فتح الملف. يتيح لك ذلك تحسين تسجيل الأمر الخاص بك للحالات الواسعة كما قلت أعلاه.

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

أعتقد أنه يمكنك استخدام Text Diff for XML خاصة في حالتك، حيث سيقوم الإنسان بكتابة سطر XML حسب الخط. لا أعرف المعلومات التي تقولها أنك لا تستطيع أن تفعل ذلك ولكن أعتقد أن البيان استنادا إلى حقيقة أن الأحرف الفضائية (الفضاء أو علامة التبويب أو نيولينيا ...) مختلفة إلى حد ما أنها موجودة في ملف نصي عادي يمكن أن يؤدي إلى اثنين من الملفات النصية المختلفة متطابقة من وجهة نظر XML. ولكن مرة أخرى، للحصول على محرر يستهدف الإنسان، لا أرى لماذا لا يمكنك ذلك.

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