Biểu đồ phân tán Matplotlib với văn bản khác nhau tại mỗi điểm dữ liệu


252

Tôi đang cố gắng tạo một biểu đồ phân tán và chú thích các điểm dữ liệu với các số khác nhau từ một danh sách. Vì vậy, ví dụ, tôi muốn vẽ biểu đồ yvs xvà chú thích với các số tương ứng từ n.

y = [2.56422, 3.77284, 3.52623, 3.51468, 3.02199]
z = [0.15, 0.3, 0.45, 0.6, 0.75]
n = [58, 651, 393, 203, 123]
ax = fig.add_subplot(111)
ax1.scatter(z, y, fmt='o')

Có ý kiến ​​gì không?


Bạn cũng có thể nhận được biểu đồ phân tán với nhãn tooltip khi di chuột bằng thư viện mpld3. mpld3.github.io/examples/scatter_tooltip.html
Claude COULOMBE

Câu trả lời:


466

Tôi không biết về bất kỳ phương pháp vẽ biểu đồ nào có mảng hoặc danh sách nhưng bạn có thể sử dụng annotate()trong khi lặp lại các giá trị trong n.

y = [2.56422, 3.77284, 3.52623, 3.51468, 3.02199]
z = [0.15, 0.3, 0.45, 0.6, 0.75]
n = [58, 651, 393, 203, 123]

fig, ax = plt.subplots()
ax.scatter(z, y)

for i, txt in enumerate(n):
    ax.annotate(txt, (z[i], y[i]))

Có rất nhiều tùy chọn định dạng cho annotate(), xem trang web matplotlib:

nhập mô tả hình ảnh ở đây


1
Hoạt động tốt trên đầu Seaborn regplotmà không bị gián đoạn quá nhiều, quá.
ijoseph

@Rutger Tôi sử dụng một datframe gấu trúc và bằng cách nào đó tôi có được một KeyError- vì vậy tôi đoán một dict()đối tượng được mong đợi? Có cách nào khác để nhãn dữ liệu sử dụng enumerate, annotatevà một khung gấu trúc dữ liệu?
Rachel

@Rachel, Bạn có thể sử dụng for row in df.iterrows():, và sau đó truy cập các giá trị, row['text'], row['x-coord']v.v ... Nếu bạn đăng một câu hỏi riêng tôi sẽ xem xét nó.
Rutger Kassies

@RutgerKassies Cảm ơn, Rutger! Tôi đã đăng một câu hỏi ở đây stackoverflow.com/questions/41481153/ Từ Tôi sợ rằng nó có thể giống với câu hỏi này. Nhưng tôi không thể giải quyết nó bằng cách nào đó. Cảm ơn sự giúp đỡ của bạn!
Rachel

1
@aviator, không tích hợp không may. Nhưng hãy xem ví dụ này bằng cách sử dụng công cụ bố cục của networkx: stackoverflow.com/a/34697108/1755432
Rutger Kassies

32

Trong phiên bản sớm hơn matplotlib 2.0, ax.scatterkhông cần thiết phải vẽ đồ thị mà không có điểm đánh dấu. Trong phiên bản 2.0, bạn sẽ cần ax.scatterđặt phạm vi và điểm đánh dấu thích hợp cho văn bản.

y = [2.56422, 3.77284, 3.52623, 3.51468, 3.02199]
z = [0.15, 0.3, 0.45, 0.6, 0.75]
n = [58, 651, 393, 203, 123]

fig, ax = plt.subplots()

for i, txt in enumerate(n):
    ax.annotate(txt, (z[i], y[i]))

Và trong liên kết này, bạn có thể tìm thấy một ví dụ trong 3d.


Điều này thật tuyệt! Cảm ơn đã chia sẻ giải pháp này. Bạn cũng có thể chia sẻ mã phù hợp để đặt kích thước của hình không? Các triển khai như plt.figure(figsize=(20,10))không hoạt động như mong đợi, trong đó việc gọi mã này không thực sự thay đổi kích thước của hình ảnh. Mong nhận được sự giúp đỡ của bạn. Cảm ơn!
Levine

fig, ax = plt.subplots (figsize = (20,10))
rafaelvalle

21

Trong trường hợp bất cứ ai đang cố gắng áp dụng các giải pháp trên cho .scatter () thay vì .subplot (),

Tôi đã thử chạy đoạn mã sau

y = [2.56422, 3.77284, 3.52623, 3.51468, 3.02199]
z = [0.15, 0.3, 0.45, 0.6, 0.75]
n = [58, 651, 393, 203, 123]

fig, ax = plt.scatter(z, y)

for i, txt in enumerate(n):
    ax.annotate(txt, (z[i], y[i]))

Nhưng gặp phải lỗi "không thể giải nén đối tượng PathCollection không thể lặp lại", với lỗi đặc biệt chỉ vào codeline fig, ax = plt.scatter (z, y)

Cuối cùng tôi đã giải quyết lỗi bằng cách sử dụng đoạn mã sau

plt.scatter(z, y)

for i, txt in enumerate(n):
    plt.annotate(txt, (z[i], y[i]))

Tôi không mong đợi có sự khác biệt giữa .scatter () và .subplot () Tôi nên biết rõ hơn.


11

Bạn cũng có thể sử dụng pyplot.text(xem tại đây ).

def plot_embeddings(M_reduced, word2Ind, words):
""" Plot in a scatterplot the embeddings of the words specified in the list "words".
    Include a label next to each point.
"""
for word in words:
    x, y = M_reduced[word2Ind[word]]
    plt.scatter(x, y, marker='x', color='red')
    plt.text(x+.03, y+.03, word, fontsize=9)
plt.show()

M_reduced_plot_test = np.array([[1, 1], [-1, -1], [1, -1], [-1, 1], [0, 0]])
word2Ind_plot_test = {'test1': 0, 'test2': 1, 'test3': 2, 'test4': 3, 'test5': 4}
words = ['test1', 'test2', 'test3', 'test4', 'test5']
plot_embeddings(M_reduced_plot_test, word2Ind_plot_test, words)

nhập mô tả hình ảnh ở đây


7

Python 3.6+:

coordinates = [('a',1,2), ('b',3,4), ('c',5,6)]
for x in coordinates: plt.annotate(x[0], (x[1], x[2]))

2

Là một lớp lót sử dụng danh sách hiểu và numpy:

[ax.annotate(x[0], (x[1], x[2])) for x in np.array([n,z,y]).T]

thiết lập là ditto cho câu trả lời của Rutger.


1

Tôi rất thích thêm rằng bạn thậm chí có thể sử dụng các mũi tên / hộp văn bản để chú thích các nhãn. Ý tôi là đây:

import random
import matplotlib.pyplot as plt


y = [2.56422, 3.77284, 3.52623, 3.51468, 3.02199]
z = [0.15, 0.3, 0.45, 0.6, 0.75]
n = [58, 651, 393, 203, 123]

fig, ax = plt.subplots()
ax.scatter(z, y)

ax.annotate(n[0], (z[0], y[0]), xytext=(z[0]+0.05, y[0]+0.3), 
    arrowprops=dict(facecolor='red', shrink=0.05))

ax.annotate(n[1], (z[1], y[1]), xytext=(z[1]-0.05, y[1]-0.3), 
    arrowprops = dict(  arrowstyle="->",
                        connectionstyle="angle3,angleA=0,angleB=-90"))

ax.annotate(n[2], (z[2], y[2]), xytext=(z[2]-0.05, y[2]-0.3), 
    arrowprops = dict(arrowstyle="wedge,tail_width=0.5", alpha=0.1))

ax.annotate(n[3], (z[3], y[3]), xytext=(z[3]+0.05, y[3]-0.2), 
    arrowprops = dict(arrowstyle="fancy"))

ax.annotate(n[4], (z[4], y[4]), xytext=(z[4]-0.1, y[4]-0.2),
    bbox=dict(boxstyle="round", alpha=0.1), 
    arrowprops = dict(arrowstyle="simple"))

plt.show()

Mà sẽ tạo ra biểu đồ sau: nhập mô tả hình ảnh ở đây

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.