MySQL中的Python foreach

时间:2016-06-05 10:05:06

标签: python mysql datetime

我试图通过Python获取MySQL中的时间戳列表。一旦我有了列表,我现在检查时间并检查哪些时间长于15分钟。有一次我有这些,我真的想要一个最终的总数。这似乎比我原先想象的更具挑战性。

所以,我使用它来从MySQL获取列表:

db = MySQLdb.connect(host=server, user=mysql_user, passwd=mysql_pwd, db=mysql_db, connect_timeout=10)
cur = db.cursor()
cur.execute("SELECT heartbeat_time FROM machines")
row = cur.fetchone()
print row
while row is not None:
    print ", ".join([str(c) for c in row])
    row = cur.fetchone()
cur.close()
db.close()

>> 2016-06-04 23:41:17
>> 2016-06-05 03:36:02
>> 2016-06-04 19:08:56

这是我用来检查它们是否超过15分钟前的片段:

fmt = '%Y-%m-%d %H:%M:%S'
d2 = datetime.strptime('2016-06-05 07:51:48', fmt)
d1 = datetime.strptime('2016-06-04 23:41:17', fmt)

d1_ts = time.mktime(d1.timetuple())
d2_ts = time.mktime(d2.timetuple())

result = int(d2_ts-d1_ts) / 60

if str(result) >= 15:
        print "more than 15m ago"

我不知道如何能够将这些结合起来。此外,既然我已经写了,那么必须有一种更简单/更好的方法来过滤这些吗?

感谢您的建议!

2 个答案:

答案 0 :(得分:2)

您可以将15分钟检查直接合并到SQL查询中。这样就没有必要乱用时间戳和IMO了,它更容易阅读代码。

如果您需要表格中其他列的某个日期:

select * from machines where now() > heartbeat_time + INTERVAL 15 MINUTE;

如果总计数是您唯一感兴趣的事情:

SELECT count(*) FROM machines WHERE NOW() > heartbeat_time + INTERVAL 15 MINUTE;

这样你就可以做一个cur.fetchone()并得到None或者一个元组,其中第一个值是时间戳大于15分钟的行数。

对于迭代结果集,写入

就足够了
cur.execute('SELECT * FROM machines')
for row in cur:
    print row

因为基本游标的行为类似于使用.fetchone()的迭代器。

(假设您在数据库中有时间戳,正如您在问题中所述)

@ user5740843:if str(result) >= 15:无法按预期工作。由于True

,因此始终为str()

答案 1 :(得分:1)

我认为heartbeat_time字段是日期时间字段。

import datetime
import MySQLdb
import MySQLdb.cursors

db = MySQLdb.connect(host=server, user=mysql_user, passwd=mysql_pwd, db=mysql_db, connect_timeout=10,
                     cursorclass=MySQLdb.cursors.DictCursor)
cur = db.cursor()

ago = datetime.datetime.utcnow() - datetime.timedelta(minutes=15)
try:
    cur.execute("SELECT heartbeat_time FROM machines")
    for row in cur:
        if row['heartbeat_time'] <= ago:
            print row['heartbeat_time'], 'more than 15 minutes ago'
finally:
    cur.close()
    db.close()

如果数据大小不是那么大,将所有数据加载到内存中是一种很好的做法,它将释放MySQL服务器上的内存缓冲区。对于DictCursor来说,之间没有这样的区别,

rows = cur.fetchall()
for r in rows: 

for r in cur:

他们都将数据加载到客户端。 MySQLdb.SSCursor和SSDictCursor将尝试根据需要传输数据,而它需要MySQL服务器来支持它。