zoukankan      html  css  js  c++  java
  • flask6 MongoDB

    flask6 MongoDB

    一.背景

    nosqll - MongoDB 文件型数据库

    文件型 - MongoDB

    User:

    [

    {id:1,name:'蔡文姬',age:16,gender:'女'},

    {id:2,name:'嫦娥',age:16,gender:'女'},

    {id:3,name:'西施',age:16,gender:'女'},

    ]

    关系型(拉里艾莉森) - MySQL MSSQL(SQLServer微软,Windows) Sybase ORACLE(MySQL被收编)(虽然是免费的,有问题,付费) DB2+AUX(IBM)

    1 . 把精力放在重要的逻辑上,细节,记住他怎么用就行! 会了逻辑,才有信心往后看。

    士别三日当刮目相待-吴下阿蒙

    2 . 不要等,主动去找事情做。

    MySQL MS - MySQL Ux

    User:

    建表 ID (int 自增 主键) name age gender

    ID name age gender
    1 蔡文姬 16
    2 嫦娥 333

    为什么开发 MongoDB呢,关系型的不好吗?

    之前的服务器级别的空间是20G,硬盘是8G,空间很小。内存8M。

    缺点:查找速度不快(之前,现在告诉硬盘14400转快了),占用空间还非常大。

    优点:

    主要是数据格式是JSON,方便传输。

    而且操作简单方便移动更加接近程序员操作(打点操作)原生语法 ORM

    因为非关系型数据库,没有结构限制(),扩展性极强

    [{id:1,name:'蔡文姬',age:16,gender:'女'},
    {id:四(不受限),name:123,age:‘十六’,gender:1,hobby:[2,3,4]},]
    
    mysql的话,有限制
    

    MongoDB数据越多,存储数据比别的数据库,占用的空间越高 ? (数据少的时候差不多)

    1.安装MongoDB

    只卖服务不卖数据库

    4版本比3版本多了个事务,还做得不是很好

    程序员读懂:exception: connect failed

    连接成功的话,cmd窗口会夯住

    三个数据库默认端口

    MongoDB  port=27017
    MYSQL   3306
    Redis   6379
    

    29 Data directory C:datadb not found., terminating

    新建C:datadb 可以的,但是200m太大了,查看帮助,新建到d盘,加到路径下

     --dbpath arg                          directory for datafiles - defaults to
                                           datadb which is C:datadb based on
                                           the current working drive
    

    CMD-

    ​ dbpath 数据库存在路径(必须存在)

    ​ mongod --dbpath D:MongoDBdatadb

    2 . 基本操作命令

    db -- 当前使用的数据库 查看名称,代指当前使用的数据库	show databases  查看当前的数据库
    use dbname    切换当前使用的数据库 或者在内存中创建一个新的数据库 赋值给db 
    show tables 	查看当前服务器磁盘上的所有数据库
    db.tablename   --  使用当前数据库中的tablename 在内存中创建表 (没有就创建,有就用了)
    

    use locall 没有也可已进去

    db.user.insert({name:'Alexander'}) show databases 就有了数据库和表

    MongoDB的特性 : 使用不存在的对象即创建该对象 (类似于python中的_setattr_)

    3 增删改查

    增
    	db.tabelname.insert({name:'123'})	#在硬盘中写入数据{name:'123'}
    	db.tabelname.insert([{name:'123'},{name:'123'}])
    查
    db.tabelname.find({查询条件})
    db.tabelname.find({name:'458'})	#查询符合条件的所有数据 
    db.stu.find({'_id':ObjectId("5d2e8f8c4e27500eac420266")})
    
    
    改
    db.tabelname.update({查询条件},{$修改器:{修改属性}})
    根据查询条件,修改第一条符合条件的值
    #修改器:认定当前修改的类型 $set设置类型修改器 强制修改某字段的值 
    db.tabelname.update({{name:'458'}},{$set:{修改属性}})
    db.tabelname.update({name:'458'},{$set:{name:789}})
    			# 双精度的
    		
    db.tabelname.update({name:'458'},{$set:{name:789}},{multi:true})   #全修改   (不提倡的写法,带参数	)
    
    删
    
    db.tabelname.remove({查询条件}) #删除所有符合条件的字段
    db.tabelname.remove({}) 	#删除所有的表
    db.tabelname.drop()			#删除整个表 
    
    删库 db.dropDatabase()	
    

    结果

    > db.tabelname.insert({name:'123'},{name:'123'})
    WriteResult({ "nInserted" : 1 })
    > db.tabelname.insert([{name:'123'},{name:'123'}])
    BulkWriteResult({
            "writeErrors" : [ ],
            "writeConcernErrors" : [ ],
            "nInserted" : 2,
            "nUpserted" : 0,
            "nMatched" : 0,
            "nModified" : 0,
            "nRemoved" : 0,
            "upserted" : [ ]
    })
    
    
    > db.tabelname.find({name:'458'})
    { "_id" : ObjectId("5d2e88cb8b6adeb6be07d5fb"), "name" : "458" }		#对象id
    

    如果已安装pip,执行pip install baidu-aip即可。

    4. MongoDB 数据类型

    ObjectID :Documents 自生成的 _id
    String: 字符串,必须是utf-8
    Boolean:布尔值,true 或者false (这里有坑哦~在我们大Python中 True False 首字母大写)
    Integer:整数 (Int32 Int64 你们就知道有个Int就行了,一般我们用Int32)	
    Double:浮点数 (没有float类型,所有小数都是Double).前后16位
    Arrays:数组或者列表,多个值存储到一个键 (list哦,大Python中的List哦)
    Object:如果你学过Python的话,那么这个概念特别好理解,就是Python中的字典,这个数据类型就是字典
    Null:空数据类型 , 一个特殊的概念,None Null
    Timestamp:时间戳
    Date:存储当前日期或时间unix时间格式 (我们一般不用这个Date类型,时间戳可以秒杀一切时间类型)
    
    MYSQL MongoDB 口语
    database database 数据库
    tables Collections
    column Field
    row Document 数据 - 一条数据
    "_id" : ObjectId("5b151f8536409809ab2e6b26")
    
    #"5b151f85" 代指的是时间戳,这条数据的产生时间(一直在变)
    #"364098" 代指某台机器的机器码,存储这条数据时的机器编号
    #"09ab" 代指进程ID,多进程存储数据的时候,非常有用的
    #"2e6b26" 代指计数器,这里要注意的是,计数器的数字可能会出现重复,不是唯一的		(是针对所有的表的)
    #以上四种标识符拼凑成世界上唯一的ObjectID
    #只要是支持MongoDB的语言,都会有一个或多个方法,对ObjectID进行转换
    #可以得到以上四种信息
    
    #注意:这个类型是不可以被JSON序列化的
    

    object 嵌套3级就好,套的再多了 就很慢

    5 数学比较符

    db.stu.find({age:{$lt:10}})

    $lt    小于
    $lte   小于等于
    $gt	   大于
    $gte   于等于
    $eq : 等于   (:不起作用时)
    $ne    不等于
    
    

    db.stu.find({age:{$lt:10}}) #并列条件查询

    6 $ 修改器+ $字符特殊用法

    MongoDB中的那些个update修改器: $inc $set $unset $push $pull

    ​ $set 修改某个字段的值

    ​ $unset 删除字段的值 db.stu.update({name:'self'},{$unset:{mytime:1}},)

    ​ $inc 引用增加 先引用 后增加

    db.stu.update({},{$inc:{age:1}}) #update只第一个人 +1

    db.stu.update({},{$inc:{age:-1}}) #年龄加 -1

    针对Array == list操作

    $push == append()

    $pushAll == extend()

    $pull == remove()

    $pop (=) pop()

    #在Array的最后一个位置增加数据
    db.stu.update({name:'小黑'},{$push:{hobbys:'站南'}} )
    #在删除Array中的指定元素
    db.stu.update({name:'小黑'},{$pull:{hobbys:'站南'}} )
    #删除Array的第一个或者最后一个元素,正数是倒序删除 负数是正序删除
    db.stu.update({name:'小黑'},{$pop:{hobbys:1}} )
     
    # 删除多个 	 
    db.stu.update({name:'小白'}, 
        {$pullAll:{hobbys:[1,2,3,4,5]}}, 
    )
    
    

    hobby.$' 符合前面的值的下标位置

    db.stu.update({'hobby':'5'},{$set:{'hobby.4':'五'}}) #4是下标,这是已知的,不知道的呢? 看下面---->

    db.stu.update({'hobby':'5'},{$set:{'hobby.$':'五'}})

    7.object 操作

    首先要有这个表 (用.取属性)

    db.stu.update({name:'小黑'},{$set:{'hobby.抽烟':'1包'}})

    object 还是 Aerry 有.属性

    db.stu.update({name:'小白','package.name':'绝世好剑'},{$inc:{'package.$.count':-1}})

    Array+Object

    $字符特殊用法

    $ 字符特殊用法
    存储当前(Array)符合条件的元素下标索引 ,只能存储最外层的 索引位置
    例子:hobbys中等于5的元素改为 "五"
    先查询到hobbys中5的 位置(2) ,将位置存储在 $==(2) 字符中 然后根据$字符的位置(2)更改数据
    db.stu.update({"hoobys":5},{ $set: {"hoobys.$":"五"} })

    上午的MongoDB语法

    db.stu.find({'_id':ObjectId("5d2e8f8c4e27500eac420266")})
    db.stu.insert(						//添加多个
    [
    {name:'小白',age:13},
    {name:'小bao',age:13}, 
    {name:'小re',age:17},
    )
    
    db.stu.find({age:{$lt:16}})			//查看小于16的年龄
    db.stu.update({age:13}, 			//改多个属性
        {$set:{name:'屡屡',gender:1}}, 
    )
    
    db.stu.find({age:20,gender:1})		//多条件查询
    
    db.stu.update({name:'self'},{$unset:{mytime:1}},) 	//删除
    
    db.stu.update({},{$inc:{age:1}})		//增加年龄
    
    db.stu.find({name:'小黑'})		//
    
    db.stu.update({name:'小黑'},{$push:{hobbys:'站南'}} )		//增加	
    db.stu.update({name:'小黑'},{$pull:{hobbys:'站南'}} )		//删除
    db.stu.update({name:'小黑'},{$pop:{hobbys:0}} )			  //删除
    
    
    db.stu.remove({})
    db.stu.find({name:'小白'}) 
    db.stu.insert([{name:'小白',age:[1,2,3,4,'5']}])	
    db.stu.update({'age':'5'},{$set:{'age.$':'五'}})			//$用法
    db.stu.find({name:'小白'})  						
    
    db.stu.update({name:'小白'},{$set:{'hobby.抽烟':'1包'}})     //.的用法
    
    db.stu.update({name:'小白','package.name':'绝世好剑'},{$inc:	{'package.$.count':-1}})										//增加属性
    db.stu.update({name:'小白','package.name':'绝世好剑'},{$inc:{'package.$.count':-1}})
    
    
    db.stu.update({name:'小白'}, 			//删除所有
        {$pullAll:{hobbys:[1,2,3,4,5]}}, 
    )
    

    查询关键字

    并列查询 and
    条件查询 or
    子集查询 all
    范围查询 in

    and
    db.stu.find({age:20,gender:1})
    db.stu.find({$and:[{name:'小白'},{age:13}]}) #位置一样顺序不一样 ,还可以加and

    or
    db.stu.find({$or:[{name:'白'},{age:13}]})

    all
    db.stu.find({'age':{$all:[1,2,3,4]}}) #全都在里面才可以

    in
    db.stu.find({name:{$in :['屡屡','小白','蓝蓝']}})

    8 . 官方给出的推荐增删改查版本

    新版3.2之后

    官方不推荐使用insert了

    db.stu.insertOne({name:'6666'}) #只能插入字典

    db.stu.insertMany([{name:777},{name:888}])

    增加数据的_id ObjectId

    增加数据的_id ObjectId 列表 [objectId,objectId]

    	insertedId: ObjectId("5d2ecd2a4e27500eac420287")
    	"insertedIds" : [
    		ObjectId("5d2ecd594e27500eac420288"),
    		ObjectId("5d2ecd594e27500eac420289")
    	]
     
    

    db.tablename.findOne({查询条件}) #返回json数据(不似转)

    db.tabelname.updateOne({{name:'458'}},{'$set':{修改属性}})

    db.tabelname.updateMany({{name:'458'}},{'$set':{修改属性}}) #修改符合条件的所有数据

    官方不推荐使用remove了

    3.2

    db.tablename.deleteOne()
    db.tablename.deleteMany()

    9 . 排序 + 选取 + 跳过

    排序:db.stu.find().sort({age:-1}) 1 正序 -1 倒叙

    选取:db.stu.find().limit(2) 选取两条数据

    跳过:db.stu.find().skip(2) 跳过前两条数据

    中间两条 or 跳过前N条

    db.stu.find().sort({age:-1}).skip(2).limit(2) #分页

    先排序 - 后跳过 - 选取 #limit最后那个 默认的

    var page = 1
    var num = 2 
    
    var sk = (page-1)*num 
    db.stu.find().sort({age:-1}).skip(sk).limit(num)
    
    

    10 . python操作MongoDB

    mysql 做不到,一列列的,MongoDB是字典的,好操作

    pop 本来就是从后往前删,所以1,正序,就是从后往前,-1就是从前往后

    作业:今天晚上+明天上午

    错误 1

    user = mdb.user.find_one({{'name':'A_C'}})
    

    TypeError: unhashable type: 'dict'

    user = mdb.user.find_one({'name':'A_C'})
    

    多加了个括号 , 错误:{{}} {} ~= get({})

    错误 ; [] 是因为查错了表,那个表里没有那个内容的

    list 可以显示出所有的表里的内容,如果没有,应该是自己没写别的内容 已经有2个,就不止是一个的。很多应该可以

    存下mongDB的值

    python操作 MongoDB

    from bson import ObjectId
    from pymongo import MongoClient		 
    from pymongo.cursor import Cursor	# 查看Cursor 
    
    import json
    
    #建立连接    
    m_client = MongoClient('127.0.0.1',27017)
    #MongoClient(host=['127.0.0.1:27017'], document_class=dict, tz_aware=False, connect=True)
    
    #连接数据库
    mdb = m_client['s20']
    #Database(MongoClient(host=['127.0.0.1:27017'], document_class=dict, tz_aware=False, connect=True), 's20')
    
    # 建立一个表
    res = mdb.user.insert_one({'name':'liuyang'})
    res.inserted_id           #5d2eee8fa456512a54ad1d07
    
    res1 = mdb.user.insert_many([{'name':'小黑'},{'name':'xiaobai'}])
    错误: 
    res1.inserted_id         #AttributeError: 'InsertManyResult' object has no attribute 'inserted_id'
    正确:
    res1.inserted_ids       #[ObjectId('5d2eef580f9d91164701f179'), ObjectId('5d2eef580f9d91164701f17a')]
    
    #增加数据时  inserted_id 和 inserted_ids 都是 ObjectId 不是字符串
    #显示的是字符串,其实是onbjectid
    
    # 查:
    res2 = mdb.user.find({})
    # 可迭代对象 : <pymongo.cursor.Cursor object at 0x0000000002F17FD0>		
    # 类似于生成器
    
    res2_list = list(res2)
    # [{'_id': ObjectId('5d2eee8fa456512a54ad1d07'), 'name': 'liuyang'}, {'_id': 
    
    for user in res2_list:
        print(user)        
     # {'_id': ObjectId('5d2eef37e08e63aaa00b3a29'), 'name': '小黑'}
     # {'_id': ObjectId('5d2eef37e08e63aaa00b3a2a'), 'name': 'xiaobai'}
    
    res3 = mdb.user.find_one({})    # find_one 是个字典啊
    print(res3,res3.get('_id'))     # {'_id': ObjectId('5d2eee8fa456512a54ad1d07'), 'name': 'liuyang'} 5d2eee8fa456512a54ad1d07  显示的是字符串,实际上是objectid
    
    res4 = mdb.user.find_one({'_id': ObjectId('5d2eee8fa456512a54ad1d07')})
    #{'_id': ObjectId('5d2eee8fa456512a54ad1d07'), 'name': 'liuyang'}
    
    
    # 转成json化,方便传输
    res_json =  json.dumps(str(res4))    
    # 列表可以被json, 但是这个列表中包含着字典  每一个字典都不行
    # TypeError: Object of type 'ObjectId' is not JSON serializable  # 是int型的因
    # "{'_id': ObjectId('5d2eee8fa456512a54ad1d07'), 'name': 'liuyang'}"
    
    
    # 错误  : 虽然类别可以,但是类别里面有不能的字典的int型   得转换了
    # res2 = list(mdb.user.find({}))
    #可迭代对象 : <pymongo.cursor.Cursor object at 0x0000000002F17FD0>
    # res_json2 = json.dumps(res2)      
    # TypeError: Object of type 'ObjectId' is not JSON serializable
    
    
    # 大体思路
    # res['_id']  = str(res.get('_id'))   
    #变成字符串 才可以被json化   flask的jsonfiy也不可以
    # print(res,str(res.get('_id')))
    # res_json = json.dumps(res)
    # print(res_json)		
    
    
    #用for循环,基于老师下面 的改
    res2 = list(mdb.user.find({}))
    for user in res2:
        user['_id'] = str(user['_id'])
    res_json4 = json.dumps(res2)
    print(res2, type(res2))     #<class 'list'>
    print(res_json4,type(res_json4))    #  <class 'str'>
    #{'_id': '5d2eef2c00e7ac7934ce1391', 'name': 'liuyang'}, {'_id': '5d2eef2c00e7ac7934ce1392', 'name': '小黑'}
    # {"_id": "5d2eef2c00e7ac7934ce1391", "name": "liuyang"}, {"_id": "5d2eef2c00e7ac7934ce1392", "name": "u5c0fu9ed1"}
    # 数据对比之下, 怎么 name变成了  二进制 json.dumps()
    
    # json.dumps输出 汉字
    res_jsonhanzi = json.dumps(res2,ensure_ascii=False)
    print(res2)
    print(res_jsonhanzi)
    
    # ASCII 编码是最简单的西文编码方案       non-ASCII
    '''
        If ``ensure_ascii`` is false, then the return value can contain non-ASCII
        characters if they appear in strings contained in ``obj``. Otherwise, all
        such characters are escaped in JSON strings.'''
    
    
    # 用for循环
    # res_list = []
    # for user in res:
    #     user['_id'] = str(user.get('_id'))
    #     res_list.append(user)
    # res_json3 = json.dumps(res_list)
    # print(res_json3)
    
    '''
    # 列表的空间节省方法的
    
    res222 = list(mdb.user.find({}))
    for index,user in enumerate(res222):
        res222[index]['_id'] = set(user.get('_id'))
    print(json.dumps(res222))
    
    ''' 
    
    # 修改数据
    res5 = mdb.user.update_one({'name': 'liuyang'}, {'$set':{'name':'A_C'}})
    # The number of documents modified.
    
    print(res5, dir(res5))
    print(res5.modified_count)   #xx.modified_count 删除和修改的时候都有       1
    
    
    print(list(mdb.user.find()))
    user = mdb.user.find_one({'name':'A_C'})
    print('user:',user)
    
    user['gender'] = 1
    user['name'] = 1
    user['hobby'] = 1
    print('user:',user)
    
    res6 = mdb.user.update_one({"name":'A_C'},{'$set':user})
    print(res6 ,dir(res6) )
    print(list(mdb.user.find({'name':'A_C'})))  # 显示的知识id和name没有别的了吗
    showAll = mdb.user.find({'name':'A_C'})
    print(dir(showAll))     # 都是cursor的
    info_xiaobai = mdb.stu.find({'name':'小白'})
    print(list(info_xiaobai))
    
    #  and  or  all 什么的太麻烦  改了塞进去
    # [{'_id': ObjectId('5d2ed07f4e27500eac420290'), 'name': '小白', 'age': [1.0, 2.0, 3.0, 4.0, '五'], 'hobby': {'抽烟': '1包'}}]
    
    # 有两个小白,导致操作不对,结果  删了一个
    # mdb.stu.delete_one({'name':'小白'})
    user2 = mdb.stu.find_one({'name':'小白'})     # 错误原因 用了find 找了一个字典
    user2['hobby'] = ['抽烟','喝酒','烫头']     # 改了知识盖的字典的,还没有改到数据库中
    # user2['hobby'].remove('抽烟')
    # print(user2['hobby'])
    # print(list(user2))
    # [{'_id': ObjectId('5d2ed0 '), 'name': '小白',  五'], 'hobby': ['喝酒', '烫头'], '抽烟': '1包'}]              # 这个 '抽烟'是字典吗
    mdb.stu.update_one({'name':'小白'},{'$set':{'hobby':user2['hobby']}})  #是添加的
    print(list(mdb.stu.find_one({'name':'小白'})))
    print(user2)
    
     
    # 删除
    # res = mdb.user.delete_one({})
    # print(res.deleted_count)          #1
    # 删除某个字段   unset 和 字典pop都行
    
    
    # 排序 + skip + limit
    res = list(mdb.stu.find())
    print(res)
    import pymongo
    res1 = mdb.stu.find().sort('age',pymongo.ASCENDING)     # ASCENDING = 1
                                                        # """Ascending sort order."""  正序
    for s in res1:
        print(s)
    res2 = list(mdb.stu.find().skip(2))         
    
    # 分页
    res3 = list(mdb.stu.find().sort('age',pymongo.ASCENDING).limit(2).skip(2))
    print('排序')
    print(res1,'
    ',res2,'
    ',res3)
    
     
    
  • 相关阅读:
    IDEA启动报错 NoClassDefFound
    IDEA手动导入jar包到maven本地库
    springboot FilterRegistrationBean 拦截器的使用
    springboot多模块controller访问的问题
    @Slf4j -- lombok.extern.slf4j.Slf4j;
    @mapper注解
    lombok
    Lodop打印小票
    spring security登录认证流程解析
    使用selenium实现简单网络爬虫抓取MM图片
  • 原文地址:https://www.cnblogs.com/Doner/p/11200251.html
Copyright © 2011-2022 走看看