zoukankan      html  css  js  c++  java
  • Python3爬虫(十) 数据存储之非关系型数据库MongoDB

     Infi-chu:

    http://www.cnblogs.com/Infi-chu/

    一、非关系型数据库
    NoSQL全程是Not Only SQL,非关系型数据库。
    NoSQL是基于键值对的,不需要经过SQL层的解析,数据之间没有耦合性,性能非常高。
    具体介绍请看(也包括Redis)

    http://www.cnblogs.com/Infi-chu/p/8277576.html

    二、MongoDB
    MongoDB 是由C++语言编写的非关系型数据库,是一个基于分布式文件存储的开源数据库系统,内容存储形式类似于JSON。

    1.连接MongoDB

    import pymongo
    client = pymongo.MongoClient(host='127.0.0.1',port=27017)    # 默认端口27017
    # 另一种写法
    client = pymongo.MongoClient('mongodb://127.0.0.1:27017')
    

    2.指定数据库
    MongoDB中可以建立很多数据库
    目前使用test数据库

    import pymongo
    client = pymongo.MongoClient(host='127.0.0.1',port=27017)
    db = client.test
    # 另一种写法
    db = client['test']
    

    3.指定集合
    MongoDB中每个数据库包含多个集合(collection),他们类似于关系型数据库中的表
    目前指定students集合

    import pymongo
    client = pymongo.MongoClient(host='127.0.0.1',port=27017)
    db = client.test
    collection = db.students
    # 另一种写法
    collection = db['students']

    4.插入数据

    student = {
    'id':'1',
    'name':'Infi-chu',
    'age':'23',
    'sex':'male'
    }
    result = collection.insert(student)
    print(result)
    

    【注】
    MongoDB中,每一条数据都有一个_id属性来唯一标识
    在PyMongo 3.x中官方不推荐使用insert()方法插入数据,
    而推荐使用insert_one()和insert_many()方法插入单条或多条数据

    student1 = {
    'id':'1',
    'name':'Infi-chu',
    'age':'23',
    'sex':'male'
    }
    student2 = {
    'id':'2',
    'name':'chu',
    'age':'23',
    'sex':'male'
    }
    result1 = collection.insert_one(student1)
    result2 = collection.insert_many([student1,student2])
    print(result1)
    print(result2)
    print(result2.inserted_ids)
    

    5.查询数据
    使用find_one()和find()方法,前者返回单条结果,后者返回一个生成器对象。
    也可以根据ObjectId来查询,此时需要bson库中的objectid

    from bson.objectid import ObjectId
    result = collection.find_one({'_id':ObjectId('这个集合的id值')})
    print(result)    # 如果结果不存在则返回None
    # 查询年龄大于20的数据
    results = collection.find('age':{'$gt':20})
    print(results)
    for result in results:
        print(result)
    
    # 通过正则表达式,查看名字以I开头的数据
    results = collection.find({'name':{'$regex':'^I.*'}})
    

    MongoDB中的比较符号
    符号       含义                                  例子
    $lt          小于            {'age':{'$lt':20}}
    $gt    大于            {'age':{'$gt':20}}
    $lte   小于等于          {'age':{'$lte':20}}
    $gte    大于等于          {'age':{'$gte':20}}
    $ne       不等于            {'age':{'$ne':20}}
    $in        在范围内           {'age':{'$in':[20,25]}}
    $nin      不在范围内          {'age':{'$nin':[20,25]}}

    MongoDB中的功能符号
    符号        含义           例子                       解释
    $regex    匹配正则表达式    {'name':{'$regex':'^I.*'}}                name以I开头
    $exists    属性是否存在     {'name':{'$exists':True}}                   name属性存在
    $type      类型判断                    {'age':{'$type':'int'}}                    age的类型是int
    $mod      数字模操作                {'age':{'$mod':[5,0]}}                        年龄模5余0
    $text       文本查询                    {'text':{'$search':'Infi-chu'}}              test类型的属性中包含Infi-chu的字符串
    $where        高级条件查询             {'where':'obj.fans_count == obj.follows_count'}             自己的粉丝数等于关注数
    $set            设置
    $inc       增长

    6.计数
    统计查询结果有多少条数据

    count = collection.find().count()
    print(count)
    

    7.排序
    排序时,直接调用sort()方法,并写明升序或降序

    results_up = collection.find().sort('name',pymongo.ASCENDING)
    result_down = collection.find().sort('name',pymongo.DESCENDING)

    8.偏移
    只想去其中某几个元素,可以使用skip()方法偏移几个位置,偏移2,就是忽略前两个元素,从第三个开始

    results = collection.find().sort('name',pymongo.ASCENDING).skip(2)
    print([result['name'] for result in results])
    # 可以使用limit()方法指定要取的结果个数
    results = collection.find().sort('name',pymongo.ASCENDING).skip(2).limit(2)
    print([result['name'] for result in results])
    '''
    【注】
    在数据库数量非常庞大的时候,不建议使用偏移量去查询,因为会导致内存溢出
    '''
    # 此时可以使用如下操作
    from bson.objectid import ObjectId
    collection.find({'_id':{$gt:ObjectId('ID号')}})
    

    9.更新

    # 使用update()方法,指定更新的条件和更新后的数据,但是官方并不推荐使用,推荐使用update_one()和update_many()方法
    condition = {'name':'Infi-chu'}
    student['age']=26
    result = collection.update(condition,student)
    print(result)
    # 使用$set对数据进行更新
    result = collection.update(condition,{'$set':student})
    print(result)
    # update_one()和update_many()
    condition = {'name':'Infi-chu'}
    student = collection.find_one(condition)
    student['age'] = 25
    result = collection.update_one(condition,{'$set':student})
    print(result)
    print(result.matched_count,result.modified_count)    # 数据条数,影响的数据条数
    

    10.删除
    使用remove()方法,推荐使用delete_one()和delete_many()

    # remove()
    result = collection.remove({'name':'Infi-chu'})
    print(result)
    # delete_one() | delete_many()
    result = collection.delete_one({'name':'Infi-chu'})
    print(result)
    print(result.deleted_count)
    result = collection.delete_many({'age':{'$lt':30}})
    print(result.deleted_count)
    

    11.更多操作
    查找后删除、替换、更新
    find_one_and_delete()
    find_one_and_replace()
    find_one_and_update()
    操作索引
    create_index()
    create_indexes()
    drop_index()

  • 相关阅读:
    看完两本书
    今夜,有点难过
    学习总结
    杂谈改变个人习惯
    最近一个月的工作学习总结
    lab项目之一阿森纳赛事指南客户端版本
    工资类程序数据库处理讨论 [数据加载(二)]
    SQL数值倍率实现问题....
    想用GDI+2.0做设计器,但在实现过程中遇到大麻烦
    这几天做工资类程序郁闷了,想写点东西理一下思路
  • 原文地址:https://www.cnblogs.com/Infi-chu/p/8980090.html
Copyright © 2011-2022 走看看