บ่อยครั้งที่ฉันพบว่าจำเป็นต้องประมวลผลรายการทีละคู่ ฉันสงสัยว่าวิธีใดจะเป็นวิธีที่มีประสิทธิภาพและมีประสิทธิภาพและพบสิ่งนี้ใน Google
pairs = zip(t[::2], t[1::2])
ฉันคิดว่านั่นเพียงพอแล้ว แต่หลังจากการสนทนาล่าสุดเกี่ยวกับสำนวนเทียบกับประสิทธิภาพฉันตัดสินใจทำการทดสอบบางอย่าง:
import time
from itertools import islice, izip
def pairs_1(t):
return zip(t[::2], t[1::2])
def pairs_2(t):
return izip(t[::2], t[1::2])
def pairs_3(t):
return izip(islice(t,None,None,2), islice(t,1,None,2))
A = range(10000)
B = xrange(len(A))
def pairs_4(t):
# ignore value of t!
t = B
return izip(islice(t,None,None,2), islice(t,1,None,2))
for f in pairs_1, pairs_2, pairs_3, pairs_4:
# time the pairing
s = time.time()
for i in range(1000):
p = f(A)
t1 = time.time() - s
# time using the pairs
s = time.time()
for i in range(1000):
p = f(A)
for a, b in p:
pass
t2 = time.time() - s
print t1, t2, t2-t1
นี่คือผลลัพธ์บนคอมพิวเตอร์ของฉัน:
1.48668909073 2.63187503815 1.14518594742
0.105381965637 1.35109519958 1.24571323395
0.00257992744446 1.46182489395 1.45924496651
0.00251388549805 1.70076990128 1.69825601578
ถ้าฉันตีความอย่างถูกต้องนั่นควรหมายความว่าการใช้รายการการจัดทำดัชนีรายการและการแบ่งส่วนรายการใน Python นั้นมีประสิทธิภาพมาก เป็นผลลัพธ์ที่ทั้งสบายใจและไม่คาดคิด
มีวิธีอื่นที่ "ดีกว่า" ในการสำรวจรายการเป็นคู่หรือไม่?
โปรดทราบว่าหากรายการมีองค์ประกอบจำนวนคี่รายการสุดท้ายจะไม่อยู่ในคู่ใด ๆ
วิธีใดเป็นวิธีที่ถูกต้องเพื่อให้แน่ใจว่าองค์ประกอบทั้งหมดรวมอยู่ด้วย
ฉันได้เพิ่มคำแนะนำสองข้อนี้จากคำตอบของการทดสอบ:
def pairwise(t):
it = iter(t)
return izip(it, it)
def chunkwise(t, size=2):
it = iter(t)
return izip(*[it]*size)
นี่คือผลลัพธ์:
0.00159502029419 1.25745987892 1.25586485863
0.00222492218018 1.23795199394 1.23572707176
ผลลัพธ์จนถึงตอนนี้
pythonic ส่วนใหญ่และมีประสิทธิภาพมาก:
pairs = izip(t[::2], t[1::2])
มีประสิทธิภาพมากที่สุดและ pythonic มาก:
pairs = izip(*[iter(t)]*2)
ฉันใช้เวลาสักครู่ในการคร่ำครวญว่าคำตอบแรกใช้ตัวทำซ้ำสองตัวในขณะที่คำตอบที่สองใช้ตัวเดียว
เพื่อจัดการกับลำดับด้วยเลขคี่ขององค์ประกอบข้อเสนอแนะที่ได้รับเพื่อเพิ่มลำดับเดิมเพิ่มองค์ประกอบหนึ่ง ( None
) itertools.izip_longest()
ที่ได้รับการจับคู่กับองค์ประกอบสุดท้ายก่อนหน้านี้สิ่งที่สามารถทำได้ด้วย
สุดท้าย
โปรดสังเกตว่าใน Python 3.x zip()
ทำงานเป็นitertools.izip()
และitertools.izip()
หายไป