แกนของกราฟเป็นสิ่งที่มีความสำคัญเพราะทำหน้าที่บอกพิกัด เราสามารถปรับเปลี่ยนแกนกราฟได้ตามที่ต้องการมากมาย
การใส่เส้นกริด เพื่อจะให้เห็นตำแหน่งอะไรต่างๆในกราฟชัดเจน บางทีสิ่งที่จำเป็นอีกอย่างก็คือเส้นกริด
การใส่เส้นกริดทำได้โดยใช้ฟังก์ชัน plt.grid หรือใช้เมธอด grid ทำกับตัว axes
import numpy as np
import matplotlib.pyplot as plt
x = np.linspace(-20,20,500)
y = 2*np.sin(x)+x/2
plt.plot(x,y,c='#111111')
plt.grid()
plt.show()
ถ้าไม่ได้ใส่คีย์เวิร์ดอะไรลงไปก็จะได้เส้นประสีดำ แต่เราสามารถปรับแต่งได้ด้วยการใส่คีย์เวิร์ดลงไป โดยใส่ได้ทั้งชื่อเต็มและย่อ
color |
c |
สี |
linestyle |
ls |
รูปแบบเส้น |
linewidth |
lw |
ความหนาเส้น |
ตัวอย่าง
theta = np.radians(np.linspace(0,720,1000))
r = np.sin(theta*5.5)
x = r*np.cos(theta)
y = r*np.sin(theta)
plt.figure(figsize=(6,6))
ax = plt.axes(facecolor='#FFEEFF')
ax.plot(x,y,c='#11AA99',lw=2)
ax.grid(c='#EE3388', ls='-', lw=2)
plt.show()
การเปลี่ยนกราฟเป็น log ปกติกราฟที่เราวาดถ้าหากไม่ได้ตั้งอะไรจะมีการจัดเรียงเป็นเชิงเส้น แต่ก็สามารถทำเป็นลอการิธึมได้ด้วย การตั้งคีย์เวิร์ด xscale และ yscale ในตอนที่สร้าง axes
ตัวอย่าง
x = np.linspace(0,5,1000)
y = 5+5*np.sin(x*50)+np.exp(x)
yticks = np.linspace(0,160,9)
yticklabels = ['%d'%s for s in yticks]
plt.figure(figsize=(6,6))
ax = plt.axes(facecolor='#EEFFEE',yscale='log',yticks=yticks,yticklabels=yticklabels)
ax.plot(x,y,c='#11AA99',lw=2)
ax.grid(c='#EE3322', ls='-.', lw=1.5)
plt.show()
ซึ่งกราฟนี้ถ้าเขียนด้วยแกนธรรมดาจะเป็นแบบนี้
x = np.linspace(0,5,1000)
y = 5+5*np.sin(x*50)+np.exp(x)
plt.figure(figsize=(6,6))
ax = plt.axes(facecolor='#EEFFEE')
ax.plot(x,y,c='#11AA99',lw=2)
ax.grid(c='#EE3322', ls='-.', lw=1.5)
plt.show()
จะปรับค่าภายหลังโดยใช้ set_xscale('log') และ set_yscale('log') ก็ได้เช่นกัน
นอกจากนี้ยังมีอีกวิธีคือไม่ต้องไปใส่คีย์เวิร์ดภายในฟังก์ชัน plt.axes แต่แค่ให้แทนที่ตรงส่วนของฟังก์ชัน plot ด้วยฟังก์ชัน semilogy สำหรับการทำให้แกน y เป็นกราฟลอการิธึม หรือใช้ similogx เพื่อทำให้แกน x เป็นลอการิธึม แต่ถ้าต้องการให้เป็นกราฟลอการิธึมทังสองแกนก็ใช้ฟังก์ชัน loglog
ตัวอย่าง
x = np.linspace(0,5,1000)
y = 5+5*np.sin(x*50)+np.exp(x)
plt.axes(aspect=1)
plt.loglog(x,y,c='#AA7799',lw=2)
plt.grid(c='#555522', ls='-.', lw=1.5)
plt.show()
จะเห็นว่าการใช้ฟังก์ชัน semilogx, semilogy และ loglog ก็ทำให้ได้กราฟลอการิธึมเช่นกัน จะเลือกใช้วิธีไหนก็แล้วแต่สะดวก ความจริงแล้วการใช้ semilogx ก็เหมือนกับเป็นการใช้ plot แล้วตามด้วย set_xscale('log') ทันทีนั่นเอง
การกลับด้านแกน x และ y หากปกติ y บวกอยู่บน ลบอยู่ล่าง x บวกอยู่ขวา ลบอยู่ซ้าย แต่เราสามารถทำให้มันสลับกันได้ด้วยเมธอด invert_xaxis และ invert_yaxis ของ axes
ตัวอย่าง
x = np.linspace(0,5,1000)
y = 15+15*np.sin(x*50)+np.exp(x)
ax = plt.axes(facecolor='#EEFFEE')
ax.plot(x,y,c='#FFAA00',lw=3)
ax.invert_yaxis()
ax.invert_xaxis()
plt.show()
การปรับแต่งขีดและเลขบอกค่า ขีดและเลขบอกค่าสามารถปรับให้เป็นรูปแบบตามที่ต้องการได้โดยใช้ฟังก์ชัน plt.tick_params หรือใช้เป็นเมธอดบนออบเจ็กต์ axes
คีย์เวิร์ดที่ใช้ได้
axis |
กำหนดว่าเป็นการตั้งค่าให้แกนไหน ถ้าไม่ระบุจะมีผลทั้งแกน x และ y |
which |
กำหนดว่าจะทำที่ขีดหลักหรือขีดย่อย (รายละเอียดอ่านบทที่ ๓๗) |
pad |
ระยะห่างระหว่างตัวเลขและแกน ถ้าใส่ค่าบวกจะออกห่างไปด้านนอก ถ้าค่าเป็นลบจะเข้าด้านใน |
labelsize |
ขนาดของตัวเลข |
colors |
สีของตัวเลขและขีด |
direction |
กำหนดว่าเส้นขีดจะอยู่ด้านในหรือด้านนอก 'in' ด้านใน 'out' ด้านนอก 'inout' ทั้งคู่ |
labelcolor |
สีของตัวเลข ถ้าไม่ได้กำหนดจะเหมือนสีขีด |
width |
ความกว้างของเส้นขีด |
length |
ความยาวของเส้นขีด |
bottom, top, left, right |
ตั้งว่าจะแสดงเส้นขีดในด้านนั้นหรือไม่ ค่าใส่เป็น 1 (True) กับ 0 (False) ค่าตั้งต้นจะแสดงแค่ซ้ายและล่าง ส่วนด้านขวาและบนไม่แสดง |
labelbottom, labeltop, labelleft, labelright |
ตั้งว่าจะแสดงข้อความในด้านนั้นหรือไม่ ค่าใส่เป็น 1 (True) กับ 0 (False) ค่าตั้งต้นจะแสดงแค่ซ้ายและล่าง ส่วนด้านขวาและบนไม่แสดง |
ตัวอย่าง
x = np.linspace(-5,5,1000)
y = (20*np.sin(x*10)+10)*np.exp(x/4)
plt.figure(figsize=(6,6),facecolor='w')
ax = plt.axes(facecolor='#FFFEEE')
ax.plot(x,y,c='#11AA99',lw=2)
ax.tick_params(colors='#11AA11',labelsize=18,bottom=0,width=2.5,length=24) # ปรับทั้งสองแกน
ax.tick_params(axis='x',pad=-120,labelcolor='b') # ปรับเพิ่มเติมเฉพาะแกน x
ax.tick_params(axis='y',labelcolor='r',direction='inout') # ปรับเพิ่มเติมเฉพาะแกน y
plt.show()
การย้ายตำแหน่งเลขบอกค่าบนแกน ปกติแล้วตัวเลขบอกค่าแกน x จะอยู่ด้านล่าง และ y จะอยู่ด้านซ้าย แต่ก็สามารถเปลี่ยนได้
คุณสมบัติต่างๆของแกน x และ y จะถูกเก็บอยู่ในออบเจ็กต์ชื่อ xaxis และ yaxis ซึ่งเป็นแอตทริบิวต์หนึ่งของ axes หากเราปรับค่าอะไรต่างๆที่ออบเจ็กต์นั้นการแสดงผลของแกนจะเปลี่ยนไป
การเปลี่ยนตำแหน่งของเลขบอกค่าแกนทำได้โดยใช้เมธอด set_ticks_position ของ xaxis และ yaxis
สำหรับ xaxis เลือกได้เป็น top กับ bottom ค่าตั้งต้นเป็น bottom
สำหรับ yaxis เลือกได้เป็น left กับ right ค่าตั้งต้นเป็น left
ลองดูตัวอย่างการปรับเลขบอกค่าไปอยู่ด้านบนและขวา
x = np.linspace(-5,5,1000)
y = (20*np.sin(x*10)+10)+x**2
ax = plt.axes(xlabel='x',ylabel='y',facecolor='#EFEEFE')
ax.plot(x,y,c='#77AA22')
ax.tick_params(labelsize=14,direction='inout',width=2.5,length=24)
ax.xaxis.set_ticks_position('top')
ax.yaxis.set_ticks_position('right')
plt.show()
นอกจากนี้ผลจากการใช้ set_ticks_position ยังทำให้เส้นขีดเหลืออยู่แค่ตำแหน่งที่เลือกเท่านั้นด้วย เช่นพอตั้งเป็น top กับ right แล้วเส้นขีดที่ฝั่งซ้ายกับล่างก็หายไป
ดังนั้นหากตั้งเป็น left กับ bottom ก็จะเป็นการลบเส้นขีดด้านขวากับบนไปด้วย
การย้ายชื่อแกน เช่นเดียวกับตำแหน่งเลขบอกค่า ตำแหน่งของชื่อแกนก็สามารถย้ายได้ในลักษณะเดียวกัน โดยใช้เมธอด set_label_position ที่ xaxis และ yaxis
สำหรับ xaxis เลือกได้เป็น top กับ bottom ค่าตั้งต้นเป็น bottom
สำหรับ yaxis เลือกได้เป็น left กับ right ค่าตั้งต้นเป็น left
ตัวอย่าง
x = np.linspace(-5,5,2000)
y = (20*np.sin(x*10)+10)+x**2
ax = plt.axes(facecolor='#EFEEFE')
ax.set_xlabel('x',fontsize=14)
ax.set_ylabel('$(20\\sin(10x)+10)+x^2$',fontsize=14)
ax.plot(x,y,c='#77AA22')
ax.tick_params(labelsize=14,direction='inout',length=12)
ax.xaxis.set_label_position('top')
ax.yaxis.set_label_position('right')
plt.show()
แต่ถ้าต้องการปรับตำแหน่งให้เป็นไปตามที่ต้องการอย่างอิสระก็ใช้เมธอด set_label_coords โดยใส่พิกัดตำแหน่งที่ต้องการวางลงไป ตำแหน่งแนวนอนไล่จากซ้ายสุดของกราฟเป็น 0 ไปจนขวาสุดเป็น 1 แนวตั้งไล่จากล่างไปบนเป็น 0 ถึง 1
ตัวอย่าง
x = np.linspace(-5,5,2000)
y = 20+20*np.sin(x*10)+(x**2)*np.exp(x/10)
ax = plt.axes(facecolor='#EFEEFE')
ax.set_xlabel('$x$',fontsize=14)
ax.set_ylabel(r'$20+20\sin(10x)+x^2e^{\frac{x}{10}}$',fontsize=14,rotation=-90)
ax.plot(x,y,c='#77AA22')
ax.tick_params(labelsize=14,direction='inout',length=10)
ax.xaxis.set_label_coords(1.05, -0.05)
ax.yaxis.set_label_coords(1.02, 0.5)
plt.show()
อนึ่ง ตำแหน่งชื่อแกน x และ y นั้นที่จริงอาจตั้งโดยใส่ค่าเป็นคีย์เวิร์ดใน set_xlabel และ set_ylabel ดังที่ได้กล่าวไปใน
บทที่แล้วก็ได้เช่นกัน ส่วนการใช้ set_label_coords นี้ก็เป็นอีกทางเลือกหนึ่ง
การย้ายตำแหน่งเส้นแกน โดยปกติแล้วเส้นแกนจะอยู่ที่ขอบบนล่างซ้ายขวา ๔ เส้น ทั้ง ๔ เส้นนี้เป็นออบเจ็กต์ที่เป็นแอตทริบิวต์หนึ่งของ axes
ออบเจ็กต์แกนทั้ง ๔ เก็บอยู่ในแอตทริบิวต์ชื่อ splines โดยแบ่งออกเป็น ๔ ตัวคือ
spines['top'] |
เส้นด้านบน |
spines['bottom'] |
เส้นด้านล่าง |
spines['left'] |
เส้นด้านซ้าย |
spines['right'] |
เส้นด้านขวา |
ตำแหน่งของเส้นแกนสามารถย้ายได้ด้วยเมธอด set_position
เมธอดนี้ต้องการอาร์กิวเมนต์เป็นคู่อันดับ (ทูเพิลหรือลิสต์) โดยเขียนเป็น (ชนิดตำแหน่ง, ค่าตำแหน่ง)
ชนิดตำแหน่งแบ่งออกเป็น ๓ ชนิดขึ้นอยู่กับว่าจะอ้างอิงอะไร
outward |
ระยะห่างจากขอบของกราฟ ถ้าค่าบวกจะไกลออกไป ถ้าค่าลบจะเข้ามาด้านใน |
axes |
อ้างอิงตำแหน่งบนฉาก โดยไล่ตั้งแต่ 0 ถึง 1 |
data |
อ้างอิงตามค่า x และ y ในกราฟ |
ลองยกตัวอย่างด้วยการวาดกราฟที่มีจุดศูนย์กลางอยู่ที่ตำแหน่ง (0,0) เราต้องการให้แกนมาอยู่
theta = np.radians(np.linspace(0,360,5000))
r = 2.5+np.sin(theta*110)+np.sin(theta*120)
x = r*np.cos(theta)
y = r*np.sin(theta)
plt.figure(figsize=(6,6))
ax = plt.axes(facecolor='#FFFFDD')
ax.plot(x,y,c='#FF5511')
ax.tick_params(labelsize=18,direction='inout')
ax.spines['bottom'].set_position(('data',0)) # ย้ายเส้นแกนซ้ายมาตรงกลาง
ax.spines['left'].set_position(('data',0)) # ย้ายเส้นแกนซ้ายมาตรงกลาง
ax.spines['right'].set_visible(0) # ซ่อนเส้นแกนขวา
ax.spines['top'].set_visible(0) # ซ่อนเส้นแกนบน
plt.show()
ในที่นี้มีการใช้เมธอด set_visible ซึ่งมีไว้ตั้งว่าจะให้แกนมองเห็นได้หรือว่าซ่อนอยู่ ถ้าตั้งเป็น 1 จะมองเห็น ถ้าเป็น 0 จะซ่อน
ดังนั้นผลที่ปรากฏจึงเห็นว่าแกนบนและขวาหายไปโดยสมบูรณ์ เหลือแค่แกนล่างกับซ้ายซึ่งมาตั้งเด่นอยู่ตรงกลาง
นอกจากนี้เส้นแกนยังมีอีกหลายอย่างที่สามารถปรับค่าได้
การตั้งค่าต่างๆของเส้นแกน นอกจากตำแหน่งแล้วเรายังสามารถตั้งค่าอะไรต่างๆของเส้นแกนได้ด้วยเมธอดต่างๆที่ขึ้นต้นด้วย set_ ได้อีกหลายอย่าง เช่น สี ,ขอบเขต, ความกว้าง, รูปแบบเส้น, ความโปร่งใส
ตัวอย่าง
plt.figure(figsize=(6,6))
ax = plt.axes(facecolor='#FFFFEF')
theta = np.radians(np.linspace(0,360,5000))
for r in np.arange(.5,10):
x = r*np.cos(theta)
y = r*np.sin(theta)
ax.plot(x,y,c='#%dF33%d1'%(9-r,r),lw=5)
ax.spines['right'].set_lw(3) # ความกว้าง
ax.spines['top'].set_lw(15) # ความกว้าง
ax.spines['top'].set_alpha(0.4) # ความโปร่งใส
ax.spines['bottom'].set_color('b') # สี
ax.spines['bottom'].set_bounds(-6,6) # ขอบเขต
ax.spines['left'].set_ls(':') # รูปแบบเส้น
plt.show()
ฟังก์ชัน setp ในการตั้งค่าอะไรต่างๆของแกนนอกจากปรับด้วยเมธอดต่างๆที่ทำกับแต่ละตัวแกนแล้วยังมีอีกวิธีคือใช้ฟังก์ชัน plt.setp
ฟังก์ชันนี้มีไว้สำหรับปรับแก้ค่าคุณสมบัติต่างๆภายในออบเจ็กต์ ข้อดีสามารถตั้งได้พร้อมกันหลายค่าพร้อมกัน
วิธีการเขียนคือใส่อาร์กิวเมนต์ตัวแรกเป็นออบเจ็กต์ที่ต้องการแก้ค่า ตัวที่สองขึ้นไปคือ คุณสมบัติที่ต้องการปรับแก้=ค่าที่ต้องการ
ตัวอย่างที่แล้วหากเปลี่ยนมาใช้ setp ก็จะเขียนเป็น
plt.setp(ax.spines['right'],linewidth=3)
plt.setp(ax.spines['top'],linewidth=15,alpha=0.4)
plt.setp(ax.spines['bottom'],color='b')
plt.setp(ax.spines['left'],ls=':')
จะเห็นว่าส่วนของ top นั้น linewidth และ alpha ถูกปรับไปพร้อมกันได้ ทำให้การเขียนสั้นลงมาก
และมีแค่ set_bounds เท่านั้นที่ไม่สามารถเขียนแทนด้วย setp ได้ เนื่องจากใช้อาร์กิวเมนต์สองตัว
นอกจากนี้ยังมีวิธีการเขียนอีกแบบคือใส่ชื่อคุณสมบัติแล้วตามด้วยค่าที่ต้องการ จากนั้นหากมีคุณสมบัติอีกตัวที่ต้องการปรับก็ใส่ต่อไปอีกสลับกันไป
ในกรณีนี้ชื่อคุณสมบัติจะต้องเขียนในรูปสายอักขระ มีเครื่องหมายคำพูดคร่อม
หากเขียนด้วยวิธีนี้จะสามารถเขียนใหม่ได้เป็น
plt.setp(ax.spines['right'],'linewidth',3)
plt.setp(ax.spines['top'],'linewidth',15,'alpha',0.4)
plt.setp(ax.spines['bottom'],'color','b')
plt.setp(ax.spines['left'],'ls',':')
ตารางสรุปค่าต่างๆที่สามารถปรับได้
ใช้เมธอด |
ใช้ setp |
ความหมาย |
set_color |
color |
ตั้งค่าสีของเส้น |
set_bounds |
- |
ตั้งขอบเขตของเส้น หน่วยเป็นไปตามค่าในเส้นกราฟ |
set_linewidth หรือ set_lw |
linewidth หรือ lw |
ตั้งความกว้างของเส้น |
set_linestyle หรือ set_ls |
linestyle หรือ ls |
ตั้งรูปแบบของเส้น |
set_alpha |
alpha |
ตั้งค่าความโปร่งใส |
set_position |
position |
ตั้งค่าตำแหน่ง (รายละเอียดเขียนในหัวข้อที่แล้ว) |
set_visible |
visible |
ตั้งให้เห็นหรือไม่เห็น: 0 ไม่เห็น 1 เห็น |
นอกจากนี้แล้วยังสามารถปรับค่าของออบเจ็กต์หลายอันพร้อมกันได้ด้วย เช่นหากต้องการปรับแกนทั้งหมดทุกอันเหมือนกันก็ใส่ [ax.spines['left'],ax.spines['right'],ax.spines['top'],ax.spines['bottom']] เป็นอาร์กิวเมนต์ตัวแรกได้เลย หรืออาจเขียนย่อเป็น [ax.spines[x] for x in ax.spines] หรือ list(ax.spines.values()) ก็ได้
ตัวอย่าง
theta = np.radians(np.linspace(0,360,5000))
r = 1+np.cos(theta*55)+np.sin(theta*60)
x = r*np.cos(theta)
y = r*np.sin(theta)
plt.figure(figsize=(6,6))
ax = plt.axes(facecolor='#DDFFFF')
ax.plot(x,y,c='#11FF11')
plt.setp([ax.spines[x] for x in ax.spines],color='#FF8800',lw=3,ls='--')
plt.show()
setp ยังใช้กับอย่างอื่นได้อีกหลายอย่าง เช่นกับ xaxis และ yaxis
ตัวอย่าง
x = np.linspace(-5,5,2000)
y = np.sin(x*20)+x**3/50
ax = plt.axes(facecolor='#FEEEFE')
ax.set_xlabel('x',fontsize=14)
ax.set_ylabel(r'$\sin(20x)+\frac{x^3}{50}$',fontsize=16,rotation=-90,labelpad=45)
ax.tick_params(labelsize=14,direction='inout',length=12)
plt.setp(ax.xaxis,label_position='top',ticks_position='bottom')
plt.setp(ax.yaxis,label_position='right',ticks_position='left')
ax.plot(x,y,c='#AA77EE')
plt.show()
อ้างอิง