您的位置:首页 > 数据库 > Mongodb

mongodb python image 图像存储读取

2013-08-07 09:59 393 查看
最近做一些数据库调研的工作,目标是实现影像更快的入库、出库、查询,并实现并行访问等操作。

将结果总结成一个mongoImg类,也算是小结吧。

'''
Created on 2013-8-6
class mongoInsert
@author: tree
'''
__metaclass__ = type

import os
from pymongo.database import Database
import time
import gridfs

class mongoImg(object):
"""mongoInsert is a class for inserting document

"""
def __init__(self, database, dir):
"""Create a new instance of :class:mongoInsert
:Parameters:
- `database`: database to use
- `dir` : directory of document
"""
if not isinstance(database, Database):
raise TypeError("database must be an instance of Database")
if len(dir) < 1:
raise TypeError("dir must be an string of directory")

#         self.__con = Connection()
self.__imgdb = database
self.__imgfs = gridfs.GridFS (self.__imgdb)
self.__dir = dir
self.__filelist=[]

#save filepath in list.txt
def __dirwalk(self,topdown=True):
"""traverse the documents of self.__dir and save in self.__filelist
"""
sum=0
self.__filelist.clear()

for root,dirs,files in os.walk(self.__dir,topdown):
for name in files:
sum+=1
temp=os.path.join(root,name)
self.__filelist.append(temp)
print(sum)

#insert image
def insert(self):
"""insert images in mongodb
"""
self.__dirwalk()

tStart = time.time()
for fi in self.__filelist:
with open (fi,'rb') as myimage:
data=myimage.read()
self.__imgfs.put(data, content_type = "jpg", filename =fi)

tEnd =time.time ()
print ("It cost %f sec" % (tEnd - tStart))

#get image by filename
def getbyname(self,filename,savepath):
"""get img from mongdb by filename
"""
if len(savepath) < 1:
raise TypeError("dir must be an string of directory")
dataout=self.__imgfs.get_version(filename)
try:
imgout=open(savepath,'wb')
data=dataout.read()
imgout.write(data)
finally:
imgout.close()


使用示例:也可以将数据库连接写在类内部

from pymongo import Connection
import mongoImg

filedir=r'D:\image'
con = Connection()
db = con.imgdb
imgmongo=mongoImg.mongoImg(db,filedir)
imgmongo.insert()


感觉mongodb存储影像切片还是蛮快的,1w多个图片,大约100-200秒左右。



tip:

gridfs.GridFS.put 函数

put(data, **kwargs)
Put data in GridFS as a new file.

Equivalent to doing:

try:
f = new_file(**kwargs)
f.write(data)
finally
f.close()


在存储读取图像时,犯了低级错误,将open得到的file实例当做数据存储,读取的时候怎么也读不出数据。。。囧

另外以字节流形式读取图像数据比较适合。

pipe = open('/dev/input/js0','rb')

如果以str形式存储的话,可能会出现UnicodeDecodeError错误,貌似是因为图像数据有些超出了python默认编码的存储区间。

ps:初学python 数据库操作也忘得差不多 欢迎大家批评和指正~
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: