Python matplotlib X轴上有多行公共日期

Python matplotlib X轴上有多行公共日期,python,arrays,datetime,matplotlib,Python,Arrays,Datetime,Matplotlib,因此,我得到了一个二维数组,每个交换机端口的历元秒数加上52个字节计数,我可以将字节计数转换为每秒兆比特数,并在数据集中以分钟为单位绘制它们: import sys import time import math import MySQLdb as mdb import numpy import matplotlib matplotlib.use('MacOSX') import matplotlib.pyplot as plt plt.grid(True) plt.ylabel('Megabi

因此,我得到了一个二维数组,每个交换机端口的历元秒数加上52个字节计数,我可以将字节计数转换为每秒兆比特数,并在数据集中以分钟为单位绘制它们:

import sys
import time
import math
import MySQLdb as mdb
import numpy
import matplotlib
matplotlib.use('MacOSX')
import matplotlib.pyplot as plt
plt.grid(True)
plt.ylabel('Megabits Per Second')
plt.xlabel('Minutes')
DBconn = mdb.connect('minotaur', 'root', '<password>', 'Monitoring')
cursor = DBconn.cursor()
sql = "select * from OfficeSwitchBytes where ComputerTime >= (unix_timestamp(now())-(60*60))"
cursor.execute(sql)
A = numpy.fromiter(cursor.fetchall(), count=-1, dtype=[('', numpy.uint32)]*53)
A = A.view(numpy.uint32).reshape(-1, 53)
(samples,ports)=A.shape
#  NO NO NO  plt.axis(xmax=samples)
print samples,ports
plotme=numpy.zeros((samples,ports-1))
for y in range(ports-1):
    for x in range(samples-1):
        seconds = A[x+1,0]-A[x,0]
        if A[x+1,y+1]>=A[x,y+1]:
            plotme[x,y] = ((A[x+1,y+1]-A[x,y+1])*8/seconds)/1e6
        else:
            print'#'
            plotme[x,y] = None
    plotme[samples-1,y] = None

plt.plot(plotme)
plt.show()

即使时间戳有点靠得很近,也能让一切正常工作。

好的,那么下面的方法就行了:

# pull data from sql, plot using matplotlib
# see http://stackoverflow.com/questions/18663746/matplotlib-multiple-lines-with-common-date-on-x-axis-solved
#
# rev 1.0 09/07/2013 WPNS cleanup from various previous hacks, first 'release'
# rev 1.1 09/07/2013 WPNS rename A to Raw
# rev 1.2 09/07/2013 WPNS make plotme the same size as Raw, so the X axis can be time
# rev 1.3 09/07/2013 WPNS add stuff from stackoverflow above
# rev 1.4 09/07/2013 WPNS cleanup, reformat
# rev 1.5 09/07/2013 WPNS combine formatted-date-time-stamp and formatting lines

import sys
import time
import math
import datetime
import MySQLdb as mdb
import numpy

# so matplotlib has to have some of the setup parameters _before_ pyplot
import matplotlib
matplotlib.use('MacOSX')
matplotlib.rcParams['figure.dpi'] = 100
matplotlib.rcParams['figure.figsize'] = [10.24, 7.68]
matplotlib.rcParams['lines.linewidth'] = 0.5
matplotlib.rcParams['axes.color_cycle'] = ['r','g','b','k']

import matplotlib.pyplot as plt

print "GraphOfficeSwitch.py V1.4 09/07/2013 WPNS",time.asctime()

# open the database connection, read the last <many> seconds of data, put them in a Numpy array called Raw
DBconn = mdb.connect('minotaur', 'root', '<password>', 'Monitoring')
cursor = DBconn.cursor()
sql = "select * from OfficeSwitchBytes where ComputerTime >= (unix_timestamp(now())-(60*60*24))"
cursor.execute(sql)
Raw = numpy.fromiter(cursor.fetchall(), count=-1, dtype=[('', numpy.uint32)]*53)
Raw = Raw.view(numpy.uint32).reshape(-1, 53)
(samples,ports)=Raw.shape
print 'Samples: {}, Ports: {}'.format(samples,ports)
plotme=numpy.zeros((samples,ports-1)) # make an array the same shape minus the epoch numbers

for y in range(ports-1):
    for x in range(samples-1):  # can't do last one, there's no delta from previous sample
        seconds = Raw[x+1,0]-Raw[x,0]
        # if the number didn't overflow the counter
        if Raw[x+1,y+1]>=Raw[x,y+1]:
            plotme[x,y] = ((Raw[x+1,y+1]-Raw[x,y+1])*8/seconds) # convert delta bytes per sample (usually a minute) to bits per second

            # convert to log scale (if zero, don't plot it)
            if plotme[x,y] > 0:
                plotme[x,y] = math.log10(plotme[x,y])
            else:
                plotme[x,y] = None

        else:
            print'#' # if the number did overflow the counter, show me
            plotme[x,y] = None # could convert it, but just don't plot for now.

    plotme[samples-1,y] = None # set last sample to "do not plot"

# get an array of adatetime objects (askewchan from stackoverflow, above)
dts = map(datetime.datetime.fromtimestamp, Raw[:,0])

plt.grid(True)
plt.ylabel('Log of Bits Per Second, 2=100bps, 9=1Gbps')
plt.axis(ymax=9,ymin=2)
plt.xlabel('Time')

plt.gca().xaxis.set_major_formatter(matplotlib.dates.DateFormatter('%m/%d %H:%M'))
plt.gca().xaxis.set_major_locator(matplotlib.dates.HourLocator())
plt.plot(dts,plotme)
plt.gcf().autofmt_xdate()
plt.show()

所以我宣布成功,非常感谢

对不起,我想这会让以后更容易找到不,这样做会让以后更难找到。请接受答案左侧的大灰色复选框,并编辑标题以删除“已解决”。
# pull data from sql, plot using matplotlib
# see http://stackoverflow.com/questions/18663746/matplotlib-multiple-lines-with-common-date-on-x-axis-solved
#
# rev 1.0 09/07/2013 WPNS cleanup from various previous hacks, first 'release'
# rev 1.1 09/07/2013 WPNS rename A to Raw
# rev 1.2 09/07/2013 WPNS make plotme the same size as Raw, so the X axis can be time
# rev 1.3 09/07/2013 WPNS add stuff from stackoverflow above
# rev 1.4 09/07/2013 WPNS cleanup, reformat
# rev 1.5 09/07/2013 WPNS combine formatted-date-time-stamp and formatting lines

import sys
import time
import math
import datetime
import MySQLdb as mdb
import numpy

# so matplotlib has to have some of the setup parameters _before_ pyplot
import matplotlib
matplotlib.use('MacOSX')
matplotlib.rcParams['figure.dpi'] = 100
matplotlib.rcParams['figure.figsize'] = [10.24, 7.68]
matplotlib.rcParams['lines.linewidth'] = 0.5
matplotlib.rcParams['axes.color_cycle'] = ['r','g','b','k']

import matplotlib.pyplot as plt

print "GraphOfficeSwitch.py V1.4 09/07/2013 WPNS",time.asctime()

# open the database connection, read the last <many> seconds of data, put them in a Numpy array called Raw
DBconn = mdb.connect('minotaur', 'root', '<password>', 'Monitoring')
cursor = DBconn.cursor()
sql = "select * from OfficeSwitchBytes where ComputerTime >= (unix_timestamp(now())-(60*60*24))"
cursor.execute(sql)
Raw = numpy.fromiter(cursor.fetchall(), count=-1, dtype=[('', numpy.uint32)]*53)
Raw = Raw.view(numpy.uint32).reshape(-1, 53)
(samples,ports)=Raw.shape
print 'Samples: {}, Ports: {}'.format(samples,ports)
plotme=numpy.zeros((samples,ports-1)) # make an array the same shape minus the epoch numbers

for y in range(ports-1):
    for x in range(samples-1):  # can't do last one, there's no delta from previous sample
        seconds = Raw[x+1,0]-Raw[x,0]
        # if the number didn't overflow the counter
        if Raw[x+1,y+1]>=Raw[x,y+1]:
            plotme[x,y] = ((Raw[x+1,y+1]-Raw[x,y+1])*8/seconds) # convert delta bytes per sample (usually a minute) to bits per second

            # convert to log scale (if zero, don't plot it)
            if plotme[x,y] > 0:
                plotme[x,y] = math.log10(plotme[x,y])
            else:
                plotme[x,y] = None

        else:
            print'#' # if the number did overflow the counter, show me
            plotme[x,y] = None # could convert it, but just don't plot for now.

    plotme[samples-1,y] = None # set last sample to "do not plot"

# get an array of adatetime objects (askewchan from stackoverflow, above)
dts = map(datetime.datetime.fromtimestamp, Raw[:,0])

plt.grid(True)
plt.ylabel('Log of Bits Per Second, 2=100bps, 9=1Gbps')
plt.axis(ymax=9,ymin=2)
plt.xlabel('Time')

plt.gca().xaxis.set_major_formatter(matplotlib.dates.DateFormatter('%m/%d %H:%M'))
plt.gca().xaxis.set_major_locator(matplotlib.dates.HourLocator())
plt.plot(dts,plotme)
plt.gcf().autofmt_xdate()
plt.show()