قائمة جميع الكلمات في القاموس أن تبدأ مع <user input="">

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

  •  02-07-2019
  •  | 
  •  

سؤال

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

مثلا:
المستخدم:"عبد"
برنامج:التنازل عن العرش ، البطن ، لاختطاف...

وذلك بفضل!


تحرير:أنا باستخدام بيثون ، ولكن أعتقد أن هذا هو إلى حد ما لغة مستقلة المشكلة.

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

المحلول

إذا كنت على ديبيان [مثل] آلة ،

#!/bin/bash
echo -n "Enter a word: "
read input
grep "^$input" /usr/share/dict/words

يأخذ كل من 0.040 s على P200.

نصائح أخرى

استخدام trie.

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

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

العقد في الرسم البياني تتوافق مع رسالة في كلمة واحدة ، لذلك كل عقدة واحد واردة رابط تصل إلى 26 (في اللغة الإنجليزية) الروابط المنتهية ولايته.

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

egrep `read input && echo ^$input` /usr/share/dict/words

يا أنا لم ترى الثعبان تحرير هنا هو نفس الشيء في بايثون

my_input = raw_input("Enter beginning of word: ")
my_words = open("/usr/share/dict/words").readlines()
my_found_words = [x for x in my_words if x[0:len(my_input)] == my_input]

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

from itertools import takewhile, islice
import bisect

def prefixes(words, pfx):
    return list(
             takewhile(lambda x: x.startswith(pfx), 
                       islice(words, 
                              bisect.bisect_right(words, pfx), 
                              len(words)))

علما أنه إنسان O(1) مع مراعاة حجم القاموس ، في حين أن هذه الخوارزمية O(log(م)) ثم O(n) فيما يتعلق عدد من السلاسل التي تبدأ فعلا مع البادئة ، في حين أن مسح كامل O(m) ، مع ن << م.

def main(script, name):
    for word in open("/usr/share/dict/words"):
        if word.startswith(name):
            print word,

if __name__ == "__main__":
    import sys
    main(*sys.argv)

إذا كنت تريد حقا أن تكون كفاءة استخدام لاحقة الأشجار أو لاحقة المصفوفات - مقالة ويكيبيديا.

مشكلتك ما لاحقة أشجار صممت للتعامل مع.هناك حتى تنفيذ بايثون هنا

var words = from word in dictionary
            where word.key.StartsWith("bla-bla-bla");
            select word;

حاول باستخدام التعابير المنطقية للبحث من خلال قائمة من الكلمات ، مثل/^كلمة/ و تقرير كل المباريات.

إذا كنت بحاجة إلى أن تكون حقا سريع استخدام الشجرة:

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

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

معظم Pythonic الحل

# set your list of words, whatever the source
words_list = ('cat', 'dog', 'banana')
# get the word from the user inpuit
user_word = raw_input("Enter a word:\n")
# create an generator, so your output is flexible and store almost nothing in memory
word_generator = (word for word in words_list if word.startswith(user_word))

# now you in, you can make anything you want with it 
# here we just list it :

for word in word_generator :
    print word

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

أفضل طريقة للقيام بذلك :

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

بيثون حصلت على آلاف من DB API تساعدك على القيام بهذه المهمة؛ -)

يمكنك استخدام str.startswith().التسجيل المستندات الرسمية:

str.startswith(بادئة [،تبدأ [نهاية]])

العودة الحقيقية إذا سلسلة تبدأ مع البادئة ، وإلا return False.بادئة يمكن أيضا أن تكون tuple من البادئات تبحث عنه.مع اختياري بدء اختبار سلسلة بداية في هذا الموقف.مع اختياري نهاية التوقف عن مقارنة سلسلة في هذا الموقف.

مثل أدناه:

user_input = input('Enter something: ')
for word in dictionary:
    if str.startswith(user_input):
        return word

إذا كان لديك قاموس كبير جدا, أقترح الفهرسة مع بيثون فهرس النص (PyLucene - علما بأنني لم تستخدم الثعبان امتداد لوسين) البحث ستكون فعالة حتى يمكن العودة البحث "النتيجة".

أيضا, إذا كان لديك قاموس هو ثابت نسبيا حتى أنك لن تضطر النفقات العامة من إعادة الفهرسة في كثير من الأحيان.

لا تستخدم بازوكا لقتل ذبابة.استخدام شيء بسيط فقط مثل سكليتي.هناك كل الأدوات التي تحتاجها كل اللغات الحديثة و يمكنك القيام به فقط :

"SELECT word FROM dict WHERE word LIKE "user_entry%"

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

بيثون توتو :

http://www.initd.org/pub/software/pysqlite/doc/usage-guide.html

خطي مسح بطيئة ، ولكن بادئة الشجرة ربما مبالغة.حفظ الكلمات فرز و باستخدام بحث ثنائي هو سريعة وبسيطة حل وسط.

import bisect
words = sorted(map(str.strip, open('/usr/share/dict/words')))
def lookup(prefix):
    return words[bisect.bisect_left(words, prefix):bisect.bisect_right(words, prefix+'~')]

>>> lookup('abdicat')
['abdicate', 'abdication', 'abdicative', 'abdicator']

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

df = pd.read_csv('dictionary.csv')
matching_words = df[0].loc[df[0].str.startswith(user_entry)] 
مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top