我试图计算数据库字符字段(PostgreSQL、pyodbc、python3.4.4、windows7)中子字符串的出现次数。但是当字符字段大于511时,count()总是返回零。只有在对返回的字符串进行“操作”之后(例如,访问索引0处的字符串或使用print()查看字符串),count()才返回预期值。长度小于等于511的字符串没有问题。你知道吗
此外,(512或更大)字符串的大小似乎会改变,请参见下面的示例。你知道吗
在使用pyodbc时,PostgreSQL、SQLite和Oracle似乎会出现这个问题。我无法用psycopg2复制它。你知道吗
那么,它是pyodbc中的一个bug吗?或者是某种优化,count()确实有问题?(其他函数似乎也可以,例如len()。)
下面的Python脚本将使用PostgreSQL、sqliteodbc或Oracle再现这个问题。 它将创建两个表,插入文本并尝试对返回的数据使用count()函数。你知道吗
import pyodbc
import sys
#conn = pyodbc.connect('driver={SQLite3 ODBC Driver}; server=localhost; database=D:\\test.db;')
#conn = pyodbc.connect('DSN=test-oracle;uid=xx;pwd=xx')
conn = pyodbc.connect('DSN=test-postgresql;uid=xx;pwd=xx')
cursor = conn.cursor()
with conn.cursor() as cursor:
cursor.execute("create table testtable511 (txt char(511) default ' ' primary key not NULL);")
cursor.execute("insert into testtable511 (txt) values ('"+511*"t"+"');")
cursor.execute("create table testtable512 (txt char(512) default ' ' primary key not NULL);")
cursor.execute("insert into testtable512 (txt) values ('"+512*"t"+"');")
cursor.execute('select * from testtable511')
data511 = cursor.fetchone()
print('511')
print(80*'#')
# count is 511, size is 560
print('counting t before "accessing" string of testtable511: ', data511[0].count('t'))
print('size of string before "accessing" string of testtable511: ', sys.getsizeof( data511[0] ))
data511[0][0]
# count is 511, size is 560
print('counting t after "accessing" string of testtable511: ', data511[0].count('t'))
print('size of string after "accessing" string of testtable511: ', sys.getsizeof( data511[0] ))
print(80*'#')
print()
cursor.execute('select * from testtable512')
data512 = cursor.fetchone()
print('512')
print(80*'#')
# count is 0, size is 1106
print('counting t before "accessing" string of testtable512: ', data512[0].count('t'))
print('size of string before "accessing" string of testtable512: ', sys.getsizeof( data512[0] ))
data512[0][0]
# count is 512, size is 593
print('counting t after "accessing" string of testtable512: ', data512[0].count('t'))
print('size of string after "accessing" string of testtable512: ', sys.getsizeof( data512[0] ))
print(80*'#')
cursor.execute("drop table testtable511;")
cursor.execute("drop table testtable512;")
conn.close()
更新:问题出在pyodbc3.0.10上。版本4.0.11修复了该问题。你知道吗
这个问题在pyodbc4.0.11中得到了修复。你知道吗
所以这似乎是早期pyodbc版本的一个bug(我使用的是3.0.10)。你知道吗
相关问题 更多 >
编程相关推荐