تقسيم الصفوف في بايثون - أفضل الممارسات؟

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

  •  09-06-2019
  •  | 
  •  

سؤال

لدي طريقة في كود Python الخاص بي تُرجع صفًا - صفًا من استعلام SQL.لنفترض أن لديها ثلاثة حقول:(معرف الوظيفة، التسمية، اسم المستخدم)

لسهولة تمريرها بين الوظائف، قمت بتمرير المجموعة بأكملها كمتغير يسمى "job".ومع ذلك، في النهاية، أريد الوصول إلى البتات، لذلك كنت أستخدم كودًا مثل هذا:(معرف الوظيفة، التسمية، اسم المستخدم) = job

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

إليك أفضل تخمينين لدي:(JobId ، Label ، اسم المستخدم) = (Job [0] ، Job [1] ، Job [2]) ... لكن هذا لا يتوسع بشكل جيد عندما يكون لديك 15 ... 20 حقلًا

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

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

المحلول

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

على سبيل المثال:

job={}
job['jobid'], job['label'], job['username']=<querycode>

نصائح أخرى

@ستايل

هناك طريقة افضل:

job = dict(zip(keys, values))

هذا سؤال قديم، ولكن...

أقترح استخدام صف مسمى في هذه الحالة: Collections.namedtuple

وهذا هو الجزء، على وجه الخصوص، الذي قد تجده مفيدًا:

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

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

سأستخدم القاموس.يمكنك تحويل tuple إلى قاموس بهذه الطريقة:

values = <querycode>
keys = ["jobid", "label", "username"]
job = dict([[keys[i], values [i]] for i in xrange(len(values ))])

سيؤدي هذا أولاً إلى إنشاء مصفوفة [["jobid"، val1]، ["label"، val2]، ["username"، val3]] ثم تحويل ذلك إلى قاموس.إذا تغير ترتيب النتائج أو عددها، فأنت بحاجة فقط إلى تغيير قائمة المفاتيح لمطابقة النتيجة الجديدة.

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

سؤال قديم، ولكن بما أنه لم يذكره أحد سأضيف هذا من كتاب بايثون للطبخ:

وصفة 81252:استخدام dtuple للوصول المرن لنتائج الاستعلام

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

مع الصف، سيكون من الصعب دائمًا إضافة الحقول أو تغييرها.أنت على حق في أن القاموس سيكون أفضل بكثير.

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

job.jobId, job.username = jobId, username

إذا كنت تستخدم حزمة MySQLdb، فيمكنك إعداد كائنات المؤشر لإرجاع الإملاءات بدلاً من الصف.

import MySQLdb, MySQLdb.cursors
conn = MySQLdb.connect(..., cursorclass=MySQLdb.cursors.DictCursor)
cur = conn.cursor() # a DictCursor
cur2 = conn.cursor(cursorclass=MySQLdb.cursors.Cursor) # a "normal" tuple cursor

وماذا عن هذا:

class TypedTuple:
    def __init__(self, fieldlist, items):
       self.fieldlist = fieldlist
       self.items = items
    def __getattr__(self, field):
       return self.items[self.fieldlist.index(field)]

يمكنك بعد ذلك القيام بما يلي:

j = TypedTuple(["jobid", "label", "username"], job)
print j.jobid

يجب أن يكون من السهل المبادلة self.fieldlist.index(field) مع البحث في القاموس في وقت لاحق ...مجرد تحرير الخاص بك __init__ طريقة!شيء مثل ستالي يفعل.

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