2015-11-12 26 views
9

Tôi đang cố tạo một ô phân tán cơ bản dựa trên một khung dữ liệu Pandas. Nhưng khi tôi gọi thường trình phân tán, tôi gặp lỗi "TypeError: promotion type invalid". mẫu mã để tạo lại vấn đề được trình bày dưới đây:Lỗi loại hình gấu trúc cố gắng để lô

t1 = pd.to_datetime('2015-11-01 00:00:00') 
t2 = pd.to_datetime('2015-11-02 00:00:00') 

Time = pd.Series([t1, t2]) 
r = pd.Series([-1, 1]) 

df = pd.DataFrame({'Time': Time, 'Value': r}) 
print(df) 

print(type(df.Time)) 
print(type(df.Time[0])) 

fig = plt.figure(figsize=(x_size,y_size)) 
ax = fig.add_subplot(111) 
ax.scatter(df.Time, y=df.Value, marker='o') 

Các kết quả đầu ra là

 Time Value 
0 2015-11-01  -1 
1 2015-11-02  1 
<class 'pandas.core.series.Series'> 
<class 'pandas.tslib.Timestamp'> 

--------------------------------------------------------------------------- 
TypeError         Traceback (most recent call last) 
<ipython-input-285-f4ed0443bf4d> in <module>() 
    15 fig = plt.figure(figsize=(x_size,y_size)) 
    16 ax = fig.add_subplot(111) 
---> 17 ax.scatter(df.Time, y=df.Value, marker='o') 

C:\Anaconda3\lib\site-packages\matplotlib\axes\_axes.py in scatter(self, x, y, s, c, marker, cmap, norm, vmin, vmax, alpha, linewidths, verts, **kwargs) 
    3635    edgecolors = 'face' 
    3636 
-> 3637   offsets = np.dstack((x, y)) 
    3638 
    3639   collection = mcoll.PathCollection(

C:\Anaconda3\lib\site-packages\numpy\lib\shape_base.py in dstack(tup) 
    365 
    366  """ 
--> 367  return _nx.concatenate([atleast_3d(_m) for _m in tup], 2) 
    368 
    369 def _replace_zero_by_x_arrays(sub_arys): 

TypeError: invalid type promotion 

Tìm kiếm xung quanh tôi đã tìm thấy một bài tương tự Pandas Series TypeError and ValueError when using datetime điều này gợi ý rằng lỗi là do có nhiều kiểu dữ liệu trong chuỗi. Nhưng điều đó dường như không phải là vấn đề trong ví dụ của tôi, được chứng minh bằng thông tin loại tôi đang in.

Lưu ý rằng nếu tôi ngừng sử dụng các đối tượng ngày giờ của gấu trúc và làm cho 'Thời gian' trở thành phao thay vì điều này hoạt động tốt, ví dụ:

t1 = 1.1 # 
t2 = 1.2 

Time = pd.Series([t1, t2]) 
r = pd.Series([-1, 1]) 

df = pd.DataFrame({'Time': Time, 'Value': r}) 
print(df) 

print(type(df.Time)) 
print(type(df.Time[0])) 

fig = plt.figure(figsize=(x_size,y_size)) 
ax = fig.add_subplot(111) 
ax.scatter(df.Time, y=df.Value, marker='o') 

với sản lượng

Time Value 
0 1.1  -1 
1 1.2  1 
<class 'pandas.core.series.Series'> 
<class 'numpy.float64'> 

và đồ thị trông giống tốt. Tôi đang thua lỗ là tại sao việc sử dụng datetime lại gây ra lỗi quảng bá loại không hợp lệ? Tôi đang sử dụng Python 3.4.3 và gấu trúc 0.16.2.

Trả lời

6

Cảm ơn @martinvseticka. Tôi nghĩ rằng đánh giá của bạn là chính xác dựa trên mã numpy bạn chỉ cho tôi. Tôi đã có thể đơn giản hóa các chỉnh sửa của bạn nhiều hơn một chút (và thêm một điểm mẫu thứ ba) để có được

t1 = pd.to_datetime('2015-11-01 00:00:00') 
t2 = pd.to_datetime('2015-11-02 00:00:00') 
t3 = pd.to_datetime('2015-11-03 00:00:00') 

Time = pd.Series([t1, t2, t3]) 
r = pd.Series([-1, 1, 0.5]) 

df = pd.DataFrame({'Time': Time, 'Value': r}) 

fig = plt.figure(figsize=(x_size,y_size)) 
ax = fig.add_subplot(111) 
ax.plot_date(x=df.Time, y=df.Value, marker='o') 

Phím có vẻ là gọi 'plot_date' thay vì 'plot'. Điều này dường như thông báo cho mapplotlib không cố gắng ghép các mảng.

+0

Tôi rất vui vì bạn đã giải quyết nó. Tốt công việc :) –

+0

Tôi đề nghị chấp nhận câu trả lời của riêng bạn nếu nó cung cấp một giải pháp đầy đủ cho câu hỏi của bạn. Điều này sẽ chỉ ra cho hệ thống rằng câu hỏi được giải quyết. –

3

Đây có phải là những gì bạn đang tìm kiếm không?

import numpy as np 
import pandas as pd 
import matplotlib.pyplot as plt 
import matplotlib.dates as dates 

t1 = pd.to_datetime('2015-11-01 00:00:00') 
t2 = pd.to_datetime('2015-11-02 00:00:00') 

idx = pd.Series([t1, t2]) 
s = pd.Series([-1, 1], index=idx) 

fig, ax = plt.subplots() 
ax.plot_date(idx, s, 'v-') 
plt.tight_layout() 
plt.show() 

Tôi mới dùng Python nên hy vọng tôi không sai. Về cơ bản, tôi đã cố gắng điều chỉnh ví dụ của bạn theo https://stackoverflow.com/a/13674286/99256.

Vấn đề với kịch bản của bạn là numpytries để nối df.Timedf.Value loạt và nó không thể tìm thấy một loại phù hợp với mảng mới vì một mảng là số và thứ hai gồm Timestamp trường.

+0

Vâng, vâng, tôi đang xem xét kỹ lưỡng vấn đề này và đây thực sự là tất cả những gì tôi biết mặc dù nó không phải là giải pháp. –

+0

Cảm ơn @martinvseticka. Tôi đã có thể cập nhật đề xuất của bạn một chút (xem bên dưới). Đây chắc chắn là hành vi không trực quan - tôi đã nghĩ rằng các mảng X và Y có thể là các kiểu dữ liệu khác nhau. –

1

scatter ô có một số thuộc tính không thể mô phỏng được trong plot hoặc plot_date (vì khả năng vẽ điểm đánh dấu có kích thước khác nhau).

Chuyển đổi các chuỗi thời gian kiểu: pandas.tslib.Timestamp vào một danh sách các loại: datetime.datetime trước khi âm mưu thực hiện phân tán đã làm các trick cho tôi:

times = [d.to_pydatetime() for d in df.Time]] 
ax.scatter(times, y=df.Value, marker='o') 
1

Bạn cũng có thể làm điều gì đó như thế này:

import matplotlib.pyplot as plt 
    import numpy as np 
    import pandas as pd 
    import datetime 

    df = pd.DataFrame({"Time":["2015-11-01 00:00:00", "2015-11-02 00:00:00"], "value":[ 1, -1]}) 
    df['Time'] = pd.to_datetime(df['Time']) 
    fig, ax = plt.subplots() 
    ax.scatter(np.arange(len(df['Time'])), df['value'], marker='o') 
    ax.xaxis.set_ticks(np.arange(len(df['Time']))) 
    ax.xaxis.set_ticklabels(df['Time'], rotation=90) 
    plt.xlabel("Time") 
    plt.ylabel("value") 

    plt.show() 
2

Có một cách khác, chúng ta nên thả sử dụng Series. Chỉ cần sử dụng danh sách cho thời gian.

t1 = pd.to_datetime('2015-11-01 00:00:00') 
t2 = pd.to_datetime('2015-11-02 00:00:00') 

Time = pd.Series([t1, t2]) 
r = pd.Series([-1, 1]) 

df = pd.DataFrame({'Time': Time, 'Value': r}) 
print(df) 

print(type(df.Time)) 
print(type(df.Time[0])) 
x_size = 800 
y_size = 600 
fig = plt.figure(figsize=(x_size,y_size)) 
ax = fig.add_subplot(111) 
ax.scatter(list(df.Time.values), list(df.Value.values), marker='o') 
+0

cách tiếp cận của bạn cũng hoạt động tốt. Tôi đã chỉnh sửa nó để sửa kích thước hình và xóa các cuộc gọi rõ ràng vào danh sách (không cần thiết). –

0

Tôi đã thay đổi loại cột datetime để chuỗi trong fly:

plt.scatter(df['Date'].astype('str'), df['Category'], s=df['count']) 

và biểu đồ phân tán hoạt động. Kính trọng

Các vấn đề liên quan