私の名前はデビッドで、フロリダの救急車に勤めています。
私はPython 2.7とmatplotlibを使用しています。救急車の呼び出しのデータベースにアクセスして、各曜日に発生する呼び出しの数をカウントしようとしています。
次に、matplotlibを使用してこの情報の棒グラフを作成し、救急隊員に毎日の忙しさを視覚的に示します。
こちらIS非常にうまく機能するコード:
import pyodbc
import matplotlib.pyplot as plt
MySQLQuery = """
SELECT
DATEPART(WEEKDAY, IIU_tDispatch)AS [DayOfWeekOfCall]
, COUNT(DATEPART(WeekDay, IIU_tDispatch)) AS [DispatchesOnThisWeekday]
FROM AmbulanceIncidents
GROUP BY DATEPART(WEEKDAY, IIU_tDispatch)
ORDER BY DATEPART(WEEKDAY, IIU_tDispatch)
"""
cnxn = pyodbc.connect('DRIVER={SQL Server};SERVER=MyServer;DATABASE=MyDatabase;UID=MyUserID;PWD=MyPassword')
cursor = cnxn.cursor()
GraphCursor = cnxn.cursor()
cursor.execute(MySQLQuery)
#generate a graph to display the data
data = GraphCursor.fetchall()
DayOfWeekOfCall, DispatchesOnThisWeekday = Zip(*data)
plt.bar(DayOfWeekOfCall, DispatchesOnThisWeekday)
plt.grid()
plt.title('Dispatches by Day of Week')
plt.xlabel('Day of Week')
plt.ylabel('Number of Dispatches')
plt.show()
上記のコードは非常にうまく機能します。見栄えの良いグラフが返され、嬉しいです。私はただ一つの変更をしたいだけです。
「日曜日」などの曜日の名前を示すX軸の代わりに、整数を示します。つまり、日曜日は1、月曜日は2などです。
これに対する私の修正は、DATEPART()の代わりにDATENAME()を使用するようにSQLクエリを書き換えることです。以下に示すのは、(整数ではなく)週の名前を返すSQLコードです。
SELECT
DATENAME(WEEKDAY, IIU_tDispatch)AS [DayOfWeekOfCall]
, COUNT(DATENAME(WeekDay, IIU_tDispatch)) AS [DispatchesOnThisWeekday]
FROM AmbulanceIncidents
GROUP BY DATENAME(WEEKDAY, IIU_tDispatch)
ORDER BY DATENAME(WEEKDAY, IIU_tDispatch)
pythonコードの他のすべては同じままです。ただし、これは機能せず、エラーメッセージを理解できません。
エラーメッセージは次のとおりです。
Traceback (most recent call last):
File "C:\Documents and Settings\kulpandm\workspace\FiscalYearEndReport\CallVolumeByDayOfWeek.py", line 59, in
<module>
plt.bar(DayOfWeekOfCall, DispatchesOnThisWeekday)
File "C:\Python27\lib\site-packages\matplotlib\pyplot.py", line 2080, in bar
ret = ax.bar(left, height, width, bottom, **kwargs)
File "C:\Python27\lib\site-packages\matplotlib\axes.py", line 4740, in bar
self.add_patch(r)
File "C:\Python27\lib\site-packages\matplotlib\axes.py", line 1471, in add_patch
self._update_patch_limits(p)
File "C:\Python27\lib\site-packages\matplotlib\axes.py", line 1489, in _update_patch_limits
xys = patch.get_patch_transform().transform(vertices)
File "C:\Python27\lib\site-packages\matplotlib\patches.py", line 547, in get_patch_transform
self._update_patch_transform()
File "C:\Python27\lib\site-packages\matplotlib\patches.py", line 543, in _update_patch_transform
bbox = transforms.Bbox.from_bounds(x, y, width, height)
File "C:\Python27\lib\site-packages\matplotlib\transforms.py", line 745, in from_bounds
return Bbox.from_extents(x0, y0, x0 + width, y0 + height)
TypeError: coercing to Unicode: need string or buffer, float found
私はこれを理解できません。
要約すると、曜日を表す整数としてx軸を使用してデータを出力し、救急車事故の数のカウントを示すy軸を使用して、MatplotlibはNiceグラフを生成します。しかし、データ出力がx軸の場合、文字列(日曜日、月曜日など)になります。 Matplotlibは機能しません。
Googleで数時間調査し、matplotlibのドキュメントを読みました。これで私を助けてください。レポートエンジンとしてMatplotlibを使用したいと考えています。
あなたの質問はSQLクエリとは何の関係もありません。それは単に終了するための手段です。あなたが本当に求めているのは、pylabの棒グラフのテキストラベルを変更する方法です。 棒グラフ のドキュメントはカスタマイズに役立ちますが、単純に ラベルを変更する は最小限の作業例(MWE)です:
import pylab as plt
DayOfWeekOfCall = [1,2,3]
DispatchesOnThisWeekday = [77, 32, 42]
LABELS = ["Monday", "Tuesday", "Wednesday"]
plt.bar(DayOfWeekOfCall, DispatchesOnThisWeekday, align='center')
plt.xticks(DayOfWeekOfCall, LABELS)
plt.show()
図を変更するためだけにSQLコードを変更しないでください。代わりに、Pythonコードに少し追加してください。
この答え のようなことができると信じています。目盛りラベルを曜日に設定します。
次の行を追加するだけで簡単になります。
plt.xticks((1, 2, ..., 7), ('Sunday', 'Monday', ..., 'Saturday'))
編集:整数キーをインシデントタイプの名前にマッピングする架空のテーブルIncidentTypes
を使用したコメントへの応答の例.
cursor.execute('select incident_type_id, count(*), incident_type
from Incidents join IncidentTypes using (incident_type_id)
group by incident_type_id')
results = cursor.fetchall()
tickpositions = [int(r[0]) for r in results]
numincidents = [int(r[1]) for r in results]
ticklabels = [r[2] for r in results]
plt.bar(tickpositions, numincidents)
plt.xticks(tickpositions, ticklabels)
問題を解決した最終回答:スティーブ、ありがとうございました。とても助かりました。私はプログラミングではなく大学で地理を学んだので、これは非常に難しいです。これが私に役立つ最終的なコードです。
import pyodbc
import matplotlib.pyplot as plt
MySQLQuery = """
SELECT
DATEPART(WEEKDAY, IIU_tDispatch)AS [IntegerOfDayOfWeek]
, COUNT(DATENAME(WeekDay, IIU_tDispatch)) AS [DispatchesOnThisWeekday]
, DATENAME(WEEKDAY, IIU_tDispatch)AS [DayOfWeekOfCall]
FROM IIncidentUnitSummary
INNER JOIN PUnit ON IIU_kUnit = PUN_Unit_PK
WHERE PUN_UnitAgency = 'LC'
AND IIU_tDispatch BETWEEN 'October 1, 2010' AND 'October 1, 2011'
AND PUN_UnitID LIKE 'M__'
GROUP BY DATEPART(WEEKDAY, IIU_tDispatch), DATENAME(WEEKDAY, IIU_tDispatch)
ORDER BY DATEPART(WEEKDAY, IIU_tDispatch)
"""
cnxn = pyodbc.connect("a bunch of stuff I don't want to share")
cursor = cnxn.cursor()
GraphCursor = cnxn.cursor()
cursor.execute(MySQLQuery)
results = cursor.fetchall()
IntegerDayOfWeek, DispatchesOnThisWeekday, DayOfWeekOfCall = Zip(*results)
tickpositions = [int(r[0]) for r in results]
numincidents = [int(r[1]) for r in results]
ticklabels = [r[2] for r in results]
plt.bar(tickpositions, numincidents)
plt.xticks(tickpositions, ticklabels)
#plt.bar(DayOfWeekOfCall, DispatchesOnThisWeekday)
plt.grid()
plt.title('Dispatches by Day of Week')
plt.xlabel('Day of Week')
plt.ylabel('Number of Dispatches')
plt.show()
cursor.close()
cnxn.close()
「results = cursor.fetchall()」と、配列の作成に関係する次の4行のコードとの間の行を本当に理解していません。私はそれを見て、それがまだ沈まないので、あなたがしてくれてうれしいです。ありがとうございます。これは非常に役立ちます。デビッド