IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 大数据 -> MongoDB学习 -> 正文阅读

[大数据]MongoDB学习

1. 数据库分类

  1. 关系型数据库(RDBMS)

    • MySQL、Oracle、DB2、SQL Server
    • 关系数据库中全是表
  2. 非关系型数据库(NoSQL Not Only SQL)

    • 键值对数据库
    • 文档数据库(MongoDB)

2. MongoDB简介

  • MongoDB是一个NoSQL的数据库、是一款文档型数据库
  • 数据库指的就是一个存储数据的仓库,数据库可以使我们完成对数据的持久化的操作
  • MongoDB数据库中存储的数据的基本单位就是文档,MongoDB中存储的就是文档,所谓文档其实就是一个“JSON”
  • MongoDB中的“JSON”我们称为BSON,比普通的JSON的功能要更加的强大
  • MongoDB数据库使用的是JavaScript进行操作的,在MongoDB含有一个对ES标准实现的引擎,在MongoDB中所有ES中的语法中都可以使用

3. MongoDB下载及安装过程

3.1 MongoDB下载

  1. MongoDB下载网址:https://www.mongodb.org/dl/win32 或者 https://www.mongodb.com/try/download/community

  2. 下载最新版本即可

    在这里插入图片描述

  3. 数据库(database)

    • 数据库的服务器,服务器用来保存数据,mongod 用来启动服务器
    • 数据库的客户端,客户端用来操作服务器,对数据进行增删改查的操作,mongo 用来启动客户端

3.2 MongoDB安装过程

  1. 安装:一直next,然后安装即可

  2. 配置用户变量,在path中添加以下地址:D:\MongoDB\Server\5.0\bin

  3. 在D盘根目录:创建一个文件夹 data,在data中创建一个文件夹db

    在D盘根目录,打开cmd命令行窗口:输入 mongod 启动mongodb服务器

    自己另设data文件夹方法:mongod --dbpath 数据库路径 --port 端口号

    在这里插入图片描述

    在D盘根目录,在打开一个cmd窗口:输入 mongo 连接mongodb ,出现 >

    在这里插入图片描述

    打开的命令窗口不能关闭

  4. 将MongoDB设置为系统服务,可以自动在后台启动,不需要每次都手动启动

    https://docs.mongodb.com/manual/tutorial/install-mongodb-on-windows/

    • D盘根目录创建data,在data下创建db和log文件夹

    • 创建配置文件:在目录 D:\MongoDB\Server\5.0 下添加一个配置文件:mongod.cfg

      systemLog:
            destination: file
            path: D:\data\log\mongod.log
      storage:
            dbPath: D:\data\db
      
    • 以管理员的身份打开命令行窗口

    • 执行如下的命令

      sc.exe create MongoDB binPath= "\"D:\MongoDB\Server\5.0\bin\mongod.exe\" --service --config=\"D:\MongoDB\Server\5.0\mongod.cfg\"" DisplayName= "MongoDB" start= "auto"
      	
      sc.exe create MongoDB binPath= "\"mongod的bin目录\mongod.exe\" --service --config=\"mongo的安装目录\mongod.cfg\"" DisplayName= "MongoDB" start= "auto"
      

      执行成功会显示 [SC] CreateService 成功,然后在任务管理器中启动mongodb服务,直接在d盘根目录cmd输入mongo即可。

    • 如果启动失败,证明上边的操作有误,在控制台输入 sc delete MongoDB 删除之前配置的服务,然后从第一步再来一次

3.3 MongoDB图像化工具

下载地址:https://www.mongodbmanager.com/download

选择NoSQL Manager for MongoDB Freeware 进行下载

4. MongoDB的基本操作

4.1 基本概念

  1. 数据库(database):数据库是一个仓库,在仓库中可以存放集合。

  2. 集合(collection):集合类似于数组,在集合中可以存放文档。

  3. 文档(document):文档数据库中的最小单位,我们存储和操作的内容都是文档。

    在MongoDB中,数据库和集合都不需要手动创建,当我们创建文档时,如果文档所在的集合或数据库不存在会自动创建数据库和集合

4.2 基本指令

  1. 显示当前所有数据库:show dbs 或者 show databases
  2. 进入到指定数据库中:use 数据库名 ;使用use时,如果数据库存在则会进入到相应的数据库,如果不存在则会自动创建,一旦进入数据库,则可以使用db来引用当前库
  3. db 表示的是当前所处的数据库
  4. 显示数据库中所有的集合:show collections
  5. 启动服务器:mongod --dbpath 路径 --port 端口号
  6. 启动客户端:mongo
  7. 关闭数据库:db.shutdownServer()
  8. 创建一个新的集合:db.createCollection()
  9. 删除集合:db.collection.drop()

4.3 数据库的CRUD的操作

4.3.1 向数据库中插入文档

网址:https://docs.mongodb.com/manual/tutorial/insert-documents/

  1. db..insert(doc) --> 向集合中插入一个或多个文档(多个文档使用数组)

当我们向集合中插入文档时,如果没有给文档指定_id属性,则数据库会自动为文档添加__id,该属性用来作为文档的唯一标识

_id我们可以自己指定,如果我们指定了数据库就不会在添加了,如果自己指定__id 也必须确保它的唯一性

  1. db.collection.insertOne() --> 集合中插入一个文档

  2. db.collection.insertMany() --> 集合中插入多个文档

    例子:

    db.stus.insert({name:"猪八戒",age:28,gender:"男"});
    
    db.stus.insert([
        {name:"沙和尚",age:38,gender:"男"},
        {name:"白骨精",age:16,gender:"女"},
        {name:"蜘蛛精",age:14,gender:"女"}
    ]);
    
    db.stus.insert({_id:"hello",name:"猪八戒",age:28,gender:"男"});
    
    db.stus.find();
    
    ObjectId()
    
4.3.2 查询数据库中的文档

网址:https://docs.mongodb.com/manual/tutorial/query-documents/

  1. 查询当前集合中的所有文档:db..find() --> 可以根据指定条件从集合中查询所有符合条件的文档,返回的是一个数组。

    • find()用来查询集合中所有符合条件的文档,可以接收一个对象作为条件参数
    • {} 表示查询集合中所有的文档
    • {属性:值} 查询属性是指定值的文档
    • find()返回的是一个数组
  2. db.collection.findOne() --> 查询第一个符合条件的文档,返回的是一个对象

  3. db.collection.find().count() --> 查询符合条件的文档的数量

    例子

    db.stus.find({_id:"hello"});
    db.stus.find({age:16 , name:"白骨精"});
    db.stus.find({age:28});
    db.stus.findOne({age:28});
    db.stus.find({}).count();
    
4.3.3 修改数据库中的文档

网址:https://docs.mongodb.com/manual/tutorial/update-documents/

  1. db.collection.update(查询条件,新对象) --> 可以修改、替换集合中的一个或多个文档

    • update()默认情况下会使用新对象来替换旧的对象
    • 如果需要修改指定的属性,而不是替换需要使用“修改操作符”来完成修改
    • $set 可以用来修改文档中的指定属性
    • $unset 可以用来删除文档的指定属性
    • update()默认只会修改一个
  2. db.collection.updateOne() --> 修改集合中的一个文档

  3. db.collection.updateMany() --> 修改集合中的多个文档

  4. db.collection.replaceOne() --> 替换集合中的一个文档

    例子

    db.stus.update({name:"沙和尚"},{age:28});
    
    db.stus.update(
        {"_id" : ObjectId("6200e30487d5e91bc4d96efd")},
        {$set:{
            gender:"男",
            address:"流沙河"
        }}    
    )
    
    // 删除一个属性
    db.stus.update(
        {"_id" : ObjectId("6200e30487d5e91bc4d96efd")},
        {$unset:{
            address:1  // 值可以随便
        }}    
    )
    
    db.stus.updateMany(
        {"name" : "猪八戒"},
        {
            $set:{
                address:"猪老庄"
            }
        }    
    );
        
    db.stus.update(
        {"name" : "猪八戒"},
        {
            $set:{
            address:"呵呵呵"
            }
        },
        {
            multi:true  // multi表示是否修改多个
        }    
    )
    
    db.stus.find()
    
    
4.3.4 删除数据库的文档

网址:https://docs.mongodb.com/manual/tutorial/remove-documents/

  • db.collection.remove() --> 删除集合中的一个或多个文档(默认删除多个)

    删除一个或多个,可以第二个参数传递一个true,则只会删除一个
    如果传递一个空对象作为参数,则会删除所有的

  • db.collection.deleteOne() --> 删除集合中的一个文档

  • db.collection.deleteMany() --> 删除集合中的多个文档

  • db.collection.remove({}) --> 清空一个集合,不建议使用

  • db.collection.drop() --> 删除一个集合

  • db.dropDatabase() --> 删除一个数据库

一般数据库中的数据都不会删除,所以删除的方法很少调用, 一般会在数据中添加一个字段,来表示数据是否被删除

例子:

db.stus.remove({_id:"hello"});

db.stus.remove({age:28},true);

db.stus.insert([
    {
        name:"zbj",
        isDel:0
        },
        {
        name:"shs",
        isDel:0
        },
    {
    name:"ts",
        isDel:0
    }
]);

db.stus.updateOne({name:"ts"},{$set:{isDel:1}});
    
db.stus.find({isDel:0})    

5. MongoDB文档间的关系

  1. 一对一(one to one)

    在MongoDB中,可以通过内嵌文档的形式体现出一对一的关系

  2. 一对多(one to many)/ 多对一(many to one)

    也可以通过内嵌文档的形式体现出一对多的关系

  3. 多对多(many to many)

6. MongoDB投影和_sort

  1. 查询文档时,默认情况按照_id的值进行排序(升序)

  2. sort()可以用来指定文档的排序的规则,sort()需要传递一个对象来指定排序规则 1表示升序,-1表示降序

    db.emp.find({}).sort({sal:1});

  3. limit、skip、sort可以任意的排序进行调用

  4. 在查询时,可以在第二个参数的位置来设置查询结果的投影

    db.emp.find({},{ename:1,_id:0,sal:1});

7. mongoose简介

7.1 mongoose概念

? Mongoose就是一个让我们可以通过Node来操作MongoDB的模块。它是一个对象文档模型(ODM)库,它对Node原生的MongoDB模块进行了进一步的优化封装,并提供了更多的功能。并且在大多数情况下,它被用来把结构化的模式应用到一个MongoDB集合,并提供了验证和类型转换等好处。

7.2 mongoose好处

  • 可以为文档创建一个模式结构(Schema)
  • 可以对模型中的对象/文档进行验证
  • 数据可以通过类型转换转换为对象模型
  • 可以使用中间件来应用业务逻辑挂钩
  • 比Node原生的MongoDB驱动更容易

7.3 mongoose新对象

  1. Schema(模式对象):Schema对象定义约束了数据库中的文档结构
  2. Model:Model对象作为集合中的所有文档的表示,相当于MongoDB数据库中的集合collection
  3. Document:Document表示集合中的具体文档,相当于集合中的一个具体的文档

7.4 mongoose连接MongoDB

  1. 使用Mongoose必须先安装mongoose包:npm i mongoose --save

  2. 加载Mongoose:const mongoose = require(“mongoose”);

  3. 连接数据库:mongoose.connect(“mongodb://地址”);

    地址例子:mongodb://127.0.0.1/mg_test

  4. 断开连接:mongoose.disconnect();

    // 引入
    var mongoose = require("mongoose");
    // 连接数据库
    mongoose.connect("mongodb://127.0.0.1/my_test");
    
    mongoose.connection.once("open",function(){
      console.log("数据库连接成功~~~~~");
    });
    
    mongoose.connection.once("close",function(){
      console.log("数据库已经断开~~~~~");
    });
    
    // 断开数据库连接,一般不调用
    mongoose.disconnect();
    

Connection

  • 一旦连接了MongoDB数据库,底层的Connection对象就可以通过mongoose模块的conection属性来访问。?
  • connection对象是对数据库连接的抽象,它提供了对象连接、底层的Db对象和表示结合的Model对象的访问。
  • 并且可以对connection对象上的一些事件进行监听,来获悉数据库连接的开始与端开。
  • 比如,可以通过open和close事件来监控连接的打开和关闭。mongoose.connection.once(“open”,function(){});

7.5 Schema和Model

官网:https://mongoosejs.com/docs/guide.html

const mongoose = require("mongoose");
mongoose.connect("mongodb://127.0.0.1/my_test");
mongoose.connection.once("open",function(){
  console.log("数据库连接成功~~~~~");
});

// 将mongoose.Schema赋值给一个变量
const Schema=mongoose.Schema;
// 创建Schema(模式)对象
const stuSchema=new Schema({
  name:String,
  age:Number,
  gender:{
    type:String,
    default:"female"
  },
  address:String
});
// 通过Schema来创建Model
// Model代表的是数据库中的集合,通过Model才能对数据库进行过操作
// mongoose.model(modelName,schema)  modelName就是映射的集合名  mongoose会自动将集合名变为复数
const StuModel=mongoose.model("student",stuSchema);

// 向数据库中插入一个文档
// StuModel.create(doc,function(err){});
StuModel.create({
  name:"孙悟空",
  age:18,
  gender:"male",
  address:"花果山"
},function (err){
  if(!err){
    console.log("插入成功~~~~~")
  }
})

7.6 Model的方法

官网:https://mongoosejs.com/docs/api.html#model_Model

  1. Model.create(doc(s),[callback]); 用来创建一个或多个文档添加到数据库中

    参数:doc(s):可以是一个文档对象,也可以是文档对象的数组

    ? callback:当操作完成以后调用的毁掉函数

    StuModel.create([
      {
        name:"猪八戒",
        age:28,
        gender:"female",
        address:"高老庄"
      },{
        name:"唐僧",
        age:16,
        gender:"female",
        address:"女儿国"
      }
    ],function (err){
      if(!err){
        console.log("插入成功");
      }
    });
    
  2. Model.find(conditions, [projection], [options], [callback]); 查询所有符合条件的文档,总会返回一个数组

    Model.findById(id, [projection], [options], [callback]);根据文档的id属性查询文档

    Model.findOne(conditions, [projection], [options], [callback]);查询符合条件的第一个文档

    conditions:查询的条件;projection:投影;options:查询选项(skip,limit);callback:回调函数,查询结果通过回调函数返回,回调函数必须传,如果不传回调函数,压根不会查询

    StuModel.find({name:"唐僧"},function (err,docs){
      if(!err){
        console.log(docs);
      }
    });
    
    StuModel.find({},{name:1,_id:0},function (err,docs){
      if(!err){
        console.log(docs);
      }
    });
    
    StuModel.find({},"name age -_id",{skip:3,limit:1},function (err,docs){
      if(!err){
        console.log(docs);
      }
    });
    
    StuModel.findOne({},function (err,docs){
      if(!err){
        console.log(docs);
      }
    });
    
    StuModel.findById("62026421f4b257db26b8937b",function (err,docs){
      if(!err){
        console.log(docs);
      }
    });
    
  3. Model.update(conditions, doc, [options], [callback]);

    Model.updateMany(conditions, doc, [options], [callback]);

    Model.updateOne(conditions, doc, [options], [callback]);

    Model.replaceOne(conditions, doc, [options], [callback]);

    conditions:查询条件;doc:修改后的对象;options:配置参数;callback:回调参数

    StuModel.update({name:"唐僧"},{$set:{age:20}},function (err){
      if(!err){
        console.log("修改成功~~~");
      }
    });
    
  4. remove(conditions, [callback]);

    deleteOne(conditions, [callback]);

    deleteMany(conditions, [callback]);

    StuModel.remove({name:"白骨精"},function (err){
      if(!err){
        console.log("删除成功~~~");
      }
    });
    
  5. Model.count(conditions, [callback]);

    StuModel.count({},function (err,count){
      if(!err){
        console.log(count);
      }
    })
    

7.7 Document的方法

// 创建一个document
const stu=new StuModel({
  name:"奔波霸",
  age:48,
  gender:"male",
  address:"碧波潭"
});

// document方法
// Model.save([options],[fn])
stu.save(function (err){
  if(!err){
    console.log("保存成功~~~");
  }
})

StuModel.findOne({},function (err,doc){
  if(!err){
    /*doc.update({$set:{age:28}},function (err){
      if(!err){
        console.log("修改成功~~~");
      }
    })*/

    /*doc.age=18;
    doc.save();*/

    /*doc.remove(function (err){
      if(!err){
        console.log("删除成功~~~");
      }
    });*/

    /*console.log(doc.get("name")); // get获取文档指定属性值
    doc.set("name","朱晓晓"); // set设置文档的指定属性值
    doc.name="hahah";
    console.log(doc);
    console.log(doc._id); // _id获取文档的_id值     */

    /*console.log(doc.toJSON);  // 将Document对象转换为普通的json对象
    console.log(doc.toObject);  // 将Document对象转换为普通的js对象,转换为普通的js对象以后,所有的Document对象的方法或属性都不能使用
   */
    
    /*doc=doc.toObject();
    delete doc.address */
  }
});

7.8 mongoose的模块化

  1. 首先定义一个模块,用来连接MongoDB数据库 比如在项目中新建tools/conn_mongo.js文件

    const mongoose = require("mongoose");
    mongoose.connect("mongodb://127.0.0.1/my_test");
    mongoose.connection.once("open",function(){
      console.log("数据库连接成功~~~~~");
    });
    
  2. 新建文件index.js使用上一模块

    require("./tools/conn_mongoo");
    
  3. 新建models/student.js文件,用来定义student的模型

    require("./tools/conn_mongoo");
    const mongoose = require("mongoose");
    
    const Schema=mongoose.Schema;
    // 创建Schema(模式)对象
    const stuSchema=new Schema({
      name:String,
      age:Number,
      gender:{
        type:String,
        default:"female"
      },
      address:String
    });
    
    // 定义模型
    const StuModel=mongoose.model("student",stuSchema);
    // 导出模型
    exports.model=StuModel;
    	// module.exports=StuModel;
    
  4. 在index.js中添加以下代码

    const Student=require("./models/student").model
    	// const Student=require("./models/student")
    

8. 练习

//1.进入my_test数据库
use my_test;

//2.向数据库的users集合中插入一个文档  
db.users.insert({
    username:"sunwukong"
});

//3.查询users集合中的文档
db.users.find();

//4.向数据库的users集合中插入一个文档
db.users.insert({
    username:"zhubajie"
});
      
//5.查询数据库users集合中的文档
db.users.find();

//6.统计数据库users集合中的文档数量
db.users.find().count();

//7.查询数据库users集合中username为sunwukong的文档
db.users.find({username:"sunwukong"});

//8.向数据库users集合中的username为sunwukong的文档,添加一个address属性,属性值为huaguoshan
db.users.update({username:"sunwukong"},{$set:{address:"huaguoshan"}});

//9.使用{username:"tangseng"} 替换 username 为 zhubajie的文档
db.users.replaceOne({username:"zhubajie"},{username:"tangseng"});

//10.删除username为sunwukong的文档的address属性
db.users.update({username:"sunwukong"},{$unset:{address:1}});

//11.向username为sunwukong的文档中,添加一个hobby:{cities:["beijing","shanghai","shenzhen"] , movies:["sanguo","hero"]}
db.users.update({username:"sunwukong"},{$set:{hobby:{cities:["beijing","shanghai","shenzhen"],movies:["sanguo","hero"]}}});

//12.向username为tangseng的文档中,添加一个hobby:{movies:["A Chinese Odyssey","King of comedy"]}
db.users.update({username:"tangseng"},{$set:{hobby:{movies:["A Chinese Odyssey","King of comedy"]}}});

//13.查询喜欢电影hero的文档
// 如果通过内嵌文档来对文档进行查询,此时属性名必须使用引号
db.use.find({"hobby.movies":"hero"});

//14.向tangseng中添加一个新的电影Interstellar
// $push 向数组中添加一个新元素
// $addToSet 向数组中添加一个新元素,如果数组中已经存在该元素,则添加失败
db.users.update({username:"tangseng"},{$push:{"hobby.movies":"nterstellar"}});
db.users.update({username:"tangseng"},{$addToSet:{"hobby.movies":"nterstellar"}});

//15.删除喜欢beijing的用户
db.users.remove({"hobby.cities":"beijing"});

//16.删除users集合
db.users.remove({});
db.users.drop();
show databases;

//17.向numbers中插入20000条数据
for(var i=1;i<=20000;i++){
    db.numbers.insert({num:i});
}
db.numbers.remove({});

var arr = [];
for(var i=1;i<=20000;i++){
    arr.push({num:i});
}
db.numbers.insert(arr);
db.numbers.find();

//18.查询numbers中num为500的文档
db.numbers.find({num:500});

//19.查询numbers中num大于5000的文档
db.numbers.find({num:{$gt:500}});

//20.查询numbers中num小于30的文档
db.numbers.find({num:{$lt:30}});

//21.查询numbers中num大于40小于50的文档
db.numbers.find({num:{$gt:40,$lt:50}});

//22.查询numbers中num大于19996的文档
db.numbers.find({num:{$gt:19996}});

//23.查看numbers集合中的前10条数据
db.numbers.find({num:{$lt:10}});
db.numbers.find().limit(10);

//24.查看numbers集合中的第11条到20条数据
// skip和limit位置可以互换
db.numbers.find().skip(10).limit(10);

//25.查看numbers集合中的第21条到30条数据
db.numbers.find().skip(20).limit(10);

//26.将dept和emp集合导入到数据库中
db.dept.find();
db.emp.find();

//27.查询工资小于2000的员工
db.emp.find({sal:{$lt:2000}});

//28.查询工资在1000-2000之间的员工
db.emp.find({sal:{$lt:2000,$gt:1000}});

//29.查询工资小于1000或大于2500的员工
db.emp.find({$or:[{sal:{$lt:1000}},{sal:{$gt:2500}}]});

//30.查询财务部(depno)的所有员工
var depno = dp.dept.findOne({dname:"财务部"}).deptno;
db.emp.find({deptno:depno});

//31.查询销售部的所有员工
var depno = dp.dept.findOne({dname:"销售部"}).deptno;
db.emp.find({deptno:depno});

//32.查询所有mgr为7698的所有员工
db.emp.find({mgr:7698});

//33.为所有薪资低于1000的员工增加工资400元
db.emp.updateMany({sal:{$lt:1000}},{$inc:{sal:400}});

// skip和limit位置可以互换
db.numbers.find().skip(10).limit(10);

//25.查看numbers集合中的第21条到30条数据
db.numbers.find().skip(20).limit(10);

//26.将dept和emp集合导入到数据库中
db.dept.find();
db.emp.find();

//27.查询工资小于2000的员工
db.emp.find({sal:{$lt:2000}});

//28.查询工资在1000-2000之间的员工
db.emp.find({sal:{$lt:2000,$gt:1000}});

//29.查询工资小于1000或大于2500的员工
db.emp.find({$or:[{sal:{$lt:1000}},{sal:{$gt:2500}}]});

//30.查询财务部(depno)的所有员工
var depno = dp.dept.findOne({dname:"财务部"}).deptno;
db.emp.find({deptno:depno});

//31.查询销售部的所有员工
var depno = dp.dept.findOne({dname:"销售部"}).deptno;
db.emp.find({deptno:depno});

//32.查询所有mgr为7698的所有员工
db.emp.find({mgr:7698});

//33.为所有薪资低于1000的员工增加工资400元
db.emp.updateMany({sal:{$lt:1000}},{$inc:{sal:400}});
  大数据 最新文章
实现Kafka至少消费一次
亚马逊云科技:还在苦于ETL?Zero ETL的时代
初探MapReduce
【SpringBoot框架篇】32.基于注解+redis实现
Elasticsearch:如何减少 Elasticsearch 集
Go redis操作
Redis面试题
专题五 Redis高并发场景
基于GBase8s和Calcite的多数据源查询
Redis——底层数据结构原理
上一篇文章      下一篇文章      查看所有文章
加:2022-02-09 20:46:17  更:2022-02-09 20:48:12 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/24 13:22:21-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码