โปรเจ็กต์ Matplotlib

หน้านี้มีรายละเอียดของโครงการการเขียนเชิงเทคนิคที่ยอมรับสำหรับ Google Season of Docs

ข้อมูลสรุปของโปรเจ็กต์

องค์กรโอเพนซอร์ส:
Matplotlib
ผู้เขียนด้านเทคนิค:
Brunobeltran
ชื่อโปรเจ็กต์:
การปรับปรุงการค้นพบฟีเจอร์ด้วยการจัดทำเอกสารประเภท "โดยนัย" ให้เป็นมาตรฐาน
ระยะเวลาของโปรเจ็กต์:
วิ่งเป็นเวลานาน (5 เดือน)

คำอธิบายโปรเจ็กต์

แรงจูงใจ

ก่อนหน้านี้ API ของ matplotlib อาศัยสตริงเป็น enum มาก ""ประเภทโดยนัย" นอกจากการเลียนแบบ API ของ matlab แล้ว สตริงพารามิเตอร์เหล่านี้ยังช่วยให้ผู้ใช้ส่งผ่านค่าที่มีนัยสำคัญเป็นอาร์กิวเมนต์ไปยังฟังก์ชัน matplotlib โดยไม่ต้องนำเข้าหรือนำหน้าค่า enum จริงอย่างชัดเจน เพียงส่งผ่านตัวเลือกพล็อตพื้นฐาน (นั่นคือ plt.plot(x, y, linestyle='solid') พิมพ์ได้ง่ายกว่าและซ้ำซ้อนกว่า เช่น plt.plot(x, y, linestyle=mpl.LineStyle.solid))

ประเภทโดยนัยที่มีการระบุเป็นสตริงจำนวนมากเหล่านี้มีการพัฒนาฟีเจอร์ที่ซับซ้อนมากขึ้น ตัวอย่างเช่น ตอนนี้ linestyle สามารถเป็นสตริงหรือ 2 ชุดของลำดับ และ MarkerStyle สามารถเป็นสตริงหรือ matplotlib.path.Path ก็ได้ แม้ว่าจะเป็นเช่นนี้จริงๆ ในหลายๆ ประเภท แต่มาร์กเกอร์Style เป็นเพียงเครื่องมือเดียว (ที่เราทราบ) ที่มีสถานะของการอัปเกรดเป็นคลาส Python ที่เหมาะสม

เนื่องจากประเภทโดยนัยเหล่านี้ไม่ใช่คลาสด้วยตนเอง Matplotlib จึงต้องหมุนโซลูชันของตนเองเพื่อรวมศูนย์เอกสารและการตรวจสอบประเภทโดยนัยเหล่านี้ (เช่น รูปแบบการประมาณค่าสตริงของ docstring.interpd.update และรูปแบบโปรแกรมตรวจสอบ cbook._check_in_list ตามลำดับ) แทนการใช้เครื่องมือเชนมาตรฐานที่ได้จากคลาส Python __init__

แม้ว่าวิธีแก้ปัญหาเหล่านี้จะใช้ได้ผลดีสำหรับเรา แต่การขาดสถานที่ที่ชัดเจนในการจัดทำเอกสารโดยนัยแต่ละประเภทก็หมายความว่าเอกสารนั้นมักค้นหาได้ยาก มีตารางขนาดใหญ่ของค่าที่อนุญาตซ้ำๆ กันตลอดทั้งเอกสาร และมักจะไม่มีข้อความที่ชัดเจนเกี่ยวกับขอบเขตของประเภทโดยนัยอยู่ในเอกสาร ดูเอกสาร plt.plot เช่น ใน "หมายเหตุ" คําอธิบายวิธีการจัดรูปแบบสตริงรูปแบบ matlab พูดถึงตัวเลือก linestyle, color และ markers มีหลากหลายวิธีในการส่งผ่านค่าทั้ง 3 อย่างที่กล่าวไปแล้ว แต่สำหรับผู้ใช้หลายๆ คน สิ่งนี้เป็นแหล่งเดียวที่พวกเขาเข้าใจเกี่ยวกับค่าต่างๆ ที่เป็นไปได้สำหรับตัวเลือกเหล่านั้น จนกระทั่งเจอบทแนะนำที่เกี่ยวข้อง ตารางของแอตทริบิวต์ Line2D จะรวมอยู่เพื่อแสดงให้ผู้อ่านเห็นตัวเลือกในการควบคุมพล็อต อย่างไรก็ตาม แม้ว่ารายการ linestyle จะลิงก์กับ Line2D.set_linestyle ได้ดี (ต้องคลิก 2 คลิก) เมื่อมีการอธิบายอินพุตที่เป็นไปได้ แต่รายการ color และ markers ไม่สามารถทำได้ color เพียงลิงก์กับ Line2D.set_color ซึ่งไม่สัญชาตญาณว่าอินพุตประเภทใดบ้างที่ได้รับอนุญาต

อาจเป็นที่ถกเถียงกันว่าปัญหานี้จะแก้ไขได้ง่ายๆ ด้วยการจัดระเบียบสตริงในเอกสารแต่ละชุดที่ทำให้เกิดปัญหา แต่น่าเสียดายที่ปัญหานี้เป็นเรื่องระบบ เมื่อไม่มีศูนย์กลางในการค้นหาเอกสารประกอบ ก็ทำให้เรามีสำเนาเอกสารที่มีขนาดใหญ่ขึ้นเรื่อยๆ ซ้ำๆ ในทุกๆ ที่ที่ใช้ประเภทโดยนัยเหล่านี้ ทำให้ผู้เริ่มต้นค้นหาพารามิเตอร์ที่ต้องการได้ยากขึ้นเป็นพิเศษ อย่างไรก็ตาม ระบบปัจจุบันที่บังคับให้ผู้ใช้ค่อยๆ ปะติดปะต่อโมเดลทางความคิดสำหรับโดยปริยายแต่ละประเภทผ่านการข้ามผ่านสไตล์การดำน้ำแบบ wiki ตลอดทั้งเอกสารประกอบของเรา หรือบางส่วนจากตัวอย่าง StackOverflow ก็ถือว่าไม่ยั่งยืนเช่นกัน

เป้าหมายสิ้นสุด

ตามหลักการแล้ว การกล่าวถึงประเภทโดยปริยายใดๆ ควรลิงก์ไปยังหน้าเดียวที่อธิบายค่าที่เป็นไปได้ทั้งหมดที่ประเภทสามารถรับได้ โดยเรียงลำดับจากเรียบง่ายที่สุด พบบ่อยที่สุด ไปจนถึงขั้นสูงหรือเร้นลับ แทนที่จะใช้พื้นที่ภาพที่มีคุณค่าในเอกสาร API ระดับบนสุดเพื่อแจกแจงประเภทอินพุตที่เป็นไปได้ทั้งหมดเป็นส่วนๆ ให้กับพารามิเตอร์หนึ่งๆ เราสามารถใช้พื้นที่เดียวกันนั้นเพื่อให้คำอธิบายแบบคำง่ายๆ ว่าการวางแผนแอบสแตรกต์ที่พารามิเตอร์มีไว้ควบคุมอย่างไร

หากต้องการใช้ตัวอย่างของ linestyle อีกครั้ง สิ่งที่เราต้องการในเอกสาร LineCollection คือ

  1. ลิงก์ไปยังเอกสารฉบับเต็มสำหรับอินพุตที่อนุญาต (ชุดค่าผสมที่อยู่ใน Line2D.set_linestyle และบทแนะนำแบบแผนภูมิเส้น)
  2. คำอธิบายแบบเข้าใจง่ายเกี่ยวกับวัตถุประสงค์ของพารามิเตอร์ สำหรับผู้ใช้ขั้นสูง matplotlib ก็เห็นได้ชัดจากชื่อพารามิเตอร์ แต่ไม่จำเป็นต้องเป็นเช่นนั้นสำหรับผู้ใช้ใหม่

ลักษณะเช่นนี้ในเอกสาร LineCollection จริงคือ python """""" linestyles: `LineStyle` or list thereof, default: :rc:`lines.linestyle` ('-') A description of whether the stroke used to draw each line in the collection is dashed, dotted or solid, or some combination thereof. """""" โดยที่ Sphinx จะแก้ปัญหาการอ้างอิงประเภท LineStyle ให้ชี้ไปที่เอกสารประกอบชุดเดียวที่เชื่อถือได้และสมบูรณ์สำหรับวิธีที่ Matplotlib ปฏิบัติต่อสไตล์เส้น

ข้อดี

ตัวอย่างฟีเจอร์ที่มีประสิทธิภาพของแนวทางนี้ ได้แก่

  1. ทำให้แต่ละฟังก์ชันแสดงความสามารถที่ชัดเจนได้ในข้อความธรรมดา (ไม่ต้องคลิกเลย)
  2. การแสดงตัวเลือกเริ่มต้น (ไม่มีการคลิก) การเห็นตัวเลือกเริ่มต้นมักเพียงพอแล้ว ซึ่งจะช่วยกระตุ้นความทรงจำของผู้ใช้ที่กลับมา
  3. เขียนคำอธิบายที่สมบูรณ์ของตัวเลือก "พบบ่อยที่สุด" และ "ง่ายที่สุด" สำหรับพารามิเตอร์ที่เรียกใช้ได้ง่ายเมื่อเรียกดู (ด้วยการคลิกเพียงครั้งเดียว)
  4. ทำให้ขั้นตอนการค้นหาฟีเจอร์และวิธีการป้อนข้อมูลที่มีประสิทธิภาพมากขึ้นทำได้ง่ายๆ เพียง "เลื่อนลง" เพื่อดูตัวเลือกขั้นสูงเพิ่มเติม (ด้วยการคลิกเพียงครั้งเดียว)
  5. จัดให้มีกลยุทธ์แบบรวมศูนย์สำหรับการลิงก์เอกสาร "API" ระดับบนสุดกับ "บทแนะนำ" ที่เกี่ยวข้อง
  6. หลีกเลี่ยง API-doc-explosion ซึ่งการสแกนตัวเลือกที่เป็นไปได้มากมายสำหรับแต่ละพารามิเตอร์จะทำให้เอกสารแต่ละสตริงใช้งานยาก

ประโยชน์อื่นๆ ของวิธีการนี้แทนเอกสารปัจจุบัน ได้แก่

  1. ทำให้เอกสารมีโอกาสน้อยลงที่จะไม่อัปเดตเนื่องจากมีการรวมศูนย์
  2. การแปลง ""มาตรฐานโดยนัย"" ของ matplotlib (เช่น ""ขอบเขต" คืออะไร เทียบกับ ""ขอบเขต"") ซึ่งปัจจุบันต้องเรียนรู้จากการอ่านโค้ด
  3. กระบวนการนี้จะไฮไลต์ปัญหาความสอดคล้องกันของ API ในลักษณะที่ติดตามได้ง่ายขึ้นผ่านเครื่องมือติดตามปัญหาของ GitHub ซึ่งจะช่วยในขั้นตอนการปรับปรุง API ของเรา
  4. สร้างเอกสารได้เร็วขึ้น เนื่องจากจำนวนข้อความที่ต้องแยกวิเคราะห์ลดลงอย่างมาก

การใช้งาน

การปรับปรุงที่อธิบายไว้ข้างต้นต้องอาศัยความพยายาม 2 อย่างอย่างมาก ซึ่งจะทำให้นักเขียนด้านเทคนิคโดยเฉพาะนั้นทรงคุณค่าอย่างยิ่ง อย่างแรกคือการสร้างหน้า "บทแนะนำ" แบบรวมศูนย์ 1 หน้าตามประเภทโดยนัย ซึ่งต้องทำงานร่วมกับทีมนักพัฒนาซอฟต์แวร์หลักเพื่อค้นหารายการประเภทโดยนัยที่เป็นรูปธรรม ซึ่งเอกสารประกอบนี้จะมีคุณค่าต่อผู้ใช้ (โดยปกติเป็นเพราะฟีเจอร์ที่มีประสิทธิภาพและซ่อนอยู่ของคลังซึ่งมีเอกสารที่ปัจจุบันหาได้ในบทแนะนำที่หาเจอได้ยาก) สำหรับแต่ละโดยนัย ฉันจะสรุปบทแนะนำที่เกี่ยวข้อง เอกสาร API และหน้าตัวอย่างต่างๆ ให้เป็นแหล่งข้อมูลที่เชื่อถือได้เพียงแหล่งเดียวซึ่งสามารถลิงก์ไปยังแหล่งอ้างอิงแต่ละประเภทนั้นได้

เมื่อเอกสารส่วนกลางสำหรับประเภทโดยนัยหนึ่งๆ ครบถ้วนสมบูรณ์แล้ว การดำเนินการสำคัญอย่างที่ 2 ก็จะเริ่มขึ้น นั่นคือการแทนที่เอกสาร API ที่มีอยู่ด้วยลิงก์ไปยังเอกสารประกอบใหม่ โดยมีจุดมุ่งหมายเพื่อทำให้ประสบการณ์การใช้เอกสารใหม่นี้เป็นเรื่องง่ายที่สุดเท่าที่จะเป็นไปได้ ทั้งสำหรับผู้ที่ใช้ยูทิลิตี help() ในตัวของ Python และสำหรับผู้ที่เรียกดูเอกสารของเราทางออนไลน์

แม้ว่ารูปแบบของเอกสารประกอบที่นำเสนอในที่นี้อาจมีการเปลี่ยนแปลงเมื่อโปรเจ็กต์นี้พัฒนาไปเรื่อยๆ แต่ฉันได้ทำงานร่วมกับทีมหลักของ Matplotlib ในช่วง ""การโทรหานักพัฒนาซอฟต์แวร์"" รายสัปดาห์ เพื่อสร้างความเห็นพ้องกันว่ากลยุทธ์ที่นำเสนอที่นี่เป็นวิธีที่สะดวก เป็นประโยชน์ และจับทางได้ในเชิงเทคนิคที่สุดในการเริ่มบันทึก ""ประเภทโดยนัย" เหล่านี้ (มีหมายเหตุเกี่ยวกับการเรียกโปรแกรม mdon) ฉันจะใช้โครงสร้างพื้นฐาน "บทแนะนำ" ที่มีอยู่สำหรับขั้นตอนเริ่มต้นของการสร้างเอกสารแบบรวมศูนย์สำหรับประเภทโดยนัยแต่ละแบบ ซึ่งจะช่วยให้ฉันอ้างอิงหน้าเหล่านี้ได้ง่ายๆ ดังนี้ โดยไม่ต้องสร้างคลาสสาธารณะใหม่ (เช่น ใช้เอกสาร LineCollection เป็นตัวอย่าง)

""""""
linestyles: LineStyle or list thereof, default: :rc:`lines.linestyle` ('-')
    A description of whether the stroke used to draw each line in the collection
    is dashed, dotted or solid, or some combination thereof. For a full
    description of possible LineStyle's, see :doc:`tutorials/types/linestyle`.
""""""

จากนี้ไป เราจะเปลี่ยนวิธีการสะกดของการอ้างอิงเหล่านี้ได้อย่างง่ายดายเมื่อทีมนักพัฒนาแอปหลักเห็นด้วยกับกลยุทธ์ระยะยาวที่ดีที่สุดสำหรับการรวมเอกสารประกอบ "ประเภท" ใหม่ของเราไว้ในคลาส Python อย่างถูกต้อง ดังเช่นที่ผมได้เสนอไว้ในข้อเสนอการเพิ่มประสิทธิภาพ Matplotlib 30

สุดท้าย รายการประเภทโดยนัยที่ผมเสนอให้บันทึกใน Google ซีซันของเอกสารนี้คือ

  1. capstyle
  2. joinstyle
  3. bounds
  4. extents
  5. linestyle
  6. colors/lists of colors
  7. colornorm/colormap
  8. tick formatters

ดูเอกสารเวอร์ชันที่ใช้งานอยู่ได้ในวาทกรรมของเรา