• . NET Framework下使用MongoDB示例


    1. 新建一个控制台项目

      选择.net framework版本为4.6,最新的mongodb驱动nuget需要达到4.5.2以上,所以选择了4.6版本。

    2. 引入nuget包

      MongoDB.Driver和MongoDB.Bson

    3. MongoDB连接配置 

    // 连接地址
    string connectionStr = "mongodb://localhost:27017";
    // 数据库名
    string databaseName = "test";
    // 表名
    string dbName = "tests";
    // 创建连接
    var mongoClient = new MongoClient(connectionStr);
    var mongoDb = mongoClient.GetDatabase(databaseName);
    var collection = mongoDb.GetCollection<User>(dbName);
    

      新建了一个user类

    public class User
    {
    public string _id { get; set; }
    public int Age { get; set; }
    public string Name { get; set; }
    public User Son { get; set; }
    public DateTime BirthDateTime { get; set; }
    }
    

      

    4. 简单增删改查

    4.1 查询

    4.1.1 根据filter字段来查

      查询代码

    // 过滤条件
    var filter = Builders<User>.Filter.Eq(u => u.Name, "CeShi");
    var filterALL = Builders<User>.Filter.Where(u => u._id != null);
    
    // 查询结果
    var resultList = collection.Find(filterALL).ToList();
    Console.WriteLine("查询结果");
    
    int i = 1;
    foreach (var result in resultList)
    {
        Console.WriteLine($"//{i}");
        Console.WriteLine("{");
        Console.WriteLine($""id":"{result.id}","Age":"{result.Age}","Name":"{result.Name}",");
        Console.WriteLine(""Son":{");
        if (result.Son != null && result.Son.Age > 0)
        {
            Console.WriteLine($""Age":"{result.Son.Age}","Name":"{result.Son.Name}"");
        }
        Console.WriteLine("},");
        Console.WriteLine($""BirthDateTime":"{result.BirthDateTime}"");
        Console.WriteLine("}");
        i++;
    }
    

      第一种查询eq方式为根据条件来查的,注意这个时候会区分大小写的。第二种filter是尝试查询全部数据,但是没有找到相关方法,写的一个代替品,因为_id的值是肯定有的,所以这么写了。

      第一中查询方式结果

     

       第二种where查询结果

     4.1.2 使用linq的方式也可以进行查询

      进行全部查询,如

    //var query = from u in collection.AsQueryable()
    //                     select new { u.Name, u.age };
    
    var query = from u in collection.AsQueryable()
                        select u;
    
    var resultList = query.ToList();`
    

      这样查出的结果如下

     

       linq里可以使用where条件来过滤数据

     

       查询子文档中的数据

     

    4.2 新增

    4.2.1 添加一条数据

    // 自定义主键
    var id = Guid.NewGuid().ToString();
    
    // 要添加的数据实体
    var user = new User
    {
        _id = id,
        Age = 26,
        Name = "CeShi",
        Son = new User
        {
            Age = 1,
            Name = "ceshi"
        },
        BirthDateTime = DateTime.Now
    };
    
    //添加一条数据
    collection.InsertOne(user);`
    

      

    4.2.2 添加多条数据

     List<User> userListAdd = new List<User>();
    User userAdd1 = new User
    {
        _id = Guid.NewGuid().ToString(),
        Age = 23,
        Name = "zhangsan",
        BirthDateTime = DateTime.Now.AddYears(-22)
    };
    userListAdd.Add(userAdd1);
    
    User userAdd2 = new User
    {
        _id = Guid.NewGuid().ToString(),
        Age = 33,
        Name = "Adamas",
        Son = new User
        {
            Age = 3,
            Name = "Adams",
            BirthDateTime = DateTime.Now.AddYears(-2)
        },
        BirthDateTime = DateTime.Now.AddYears(-32)
    };
    userListAdd.Add(userAdd2);
    
    // 添加多条使用 InsertMany()方法
    collection.InsertMany(userListAdd);
    

      

    4.3 修改更新

    4.3.1 简单更新

      使用主键或其他字段进行更新,如将Name为zhagnsan的son赋值

    var filter = Builders<User>.Filter.Eq("Name", "zhangsan");
    
    var son = new User {
                            Age = 2,
                            Name = "zhangxiao",
                            BirthDateTime = DateTime.Now.AddYears(-1)
                        };
    
    // 更新数据
    var update = Builders<User>.Update.Set("Son", son);
    
    // 执行更新操作 更新一条数据
    UpdateResult upResult = collection.UpdateOne(filter, update);
    
    // 得到更新数据条数
    var upCount = upResult.ModifiedCount;`    
    

      结果如下

     

       如果想更新多条数据,则配合查询条件,使用collection.UpdateMany

    // 过滤条件
    var filter = Builders<User>.Filter.Where(u=>u.Name== "CeShi");
    
    // 更新数据
    var update = Builders<User>.Update.Set("age", "25");
    
    // 执行更新操作 更新多条
    UpdateResult upResult = collection.UpdateMany(filter, update);
    
    // 得到更新数据条数
    var upCount=upResult.ModifiedCount;
    

      

    4.3.2 根据子集合属性更新

      根据son的Name的值为“zhangxiao”,将他的年龄修改为4

    // 过滤条件
    var filter = Builders<User>.Filter.Where(u=>u.Son.Name== "zhangxiao");
    
    var son = new User
    {
        Age = 4,
        Name = "zhangxiao",
        BirthDateTime = DateTime.Now.AddYears(-3)
    };
    
    // 更新数据
    var update = Builders<User>.Update.Set("Son", son);
    
    // 执行更新操作 更新一条数据;更新多条,使用UpdateMany
    UpdateResult upResult = collection.UpdateOne(filter, update);
    
    // 得到更新数据条数
    var upCount = upResult.ModifiedCount;`
    

      结果如下

     

     4.4 删除

    4.4.1 根据主键或其他条件删除

      将name为“CeShi”的数据删除

    var filter = Builders<User>.Filter.Where(u => u.Name == "CeShi");
     // 删除一条数据
     DeleteResult deResult = collection.DeleteMany(filter); 
    // 得到删除条数 
    var deCount = deResult.DeletedCount; 
    Console.WriteLine($"删除条数{deCount.ToString()}");
    

      结果查询,已经将name为“CeShi”的数据删除了

     

     4.4.2 根据子集合属性删除

      删除子文档son里name为“zhangxiao”的数据

    var filter = Builders<User>.Filter.Where(u => u.Son.Name == "zhangxiao");
     // 删除一条数据 
    DeleteResult deResult = collection.DeleteMany(filter); 
    // 得到删除条数 
    var deCount = deResult.DeletedCount; 
    Console.WriteLine($"删除条数{deCount.ToString()}");

      结果查询,已经没有子文档son里name为“zhangxiao”的数据了

     

    5. MongoDB命令对应的操作

    5.1 $project

      $project类似于sql中的select,筛选出我们要的显示字段,如我们想选出所有数据的Name和Age字段

    var query = from p in collection.AsQueryable() 
                    select new { p.Name, p.Age };
     // 或者 
    //var query = collection.AsQueryable() 
    //         .Select(p => new { p.Name, p.Age });
    

      结果如下

     

    5.2 $sort

      排序。我们根据年龄降序和姓名升序的方式查找数据

    var query = from p in collection.AsQueryable()
                    orderby p.Name, p.Age 
                    descending select p; 
    // 或者 
    //var query = collection.AsQueryable() .OrderBy(p => p.Name).ThenByDescending(p => p.Age);
    

      结果如下

     

    5.3 $limit

    类似于linq中的take,选取多少条数据

    var query = collection.AsQueryable().Take(2);
    

      结果如下

     

    5.4 $skip

      类似于linq下的skip,跳过m条数据,配合take使用,即跳过m条数据取n条数据

    var query = collection.AsQueryable().Skip(1).Take(1);
    

      结果如下

     

    5.5 $group

      分组

    var query = from p in collection.AsQueryable() 
                    group p by p.Age into g 
                    select new { Age = g.Key, Count = g.Count() }; 
    // 或者
     //var query = collection.AsQueryable()
     // .GroupBy(p => p.Age )
     // .Select(g => new { Age = g.Key, Count = g.Count() });    
    

      结果如下

     

    5.6 $lookup 表联合查询

      类似于ef中的左连接

    var query = from u in collect.AsQueryable()
                        join o in coll.AsQueryable() on u.Name equals o.Name
                         select new { u._id, u.son, o.Id,o.Name };
     var result = query.ToList();    
    

      由于测试库没有建立第二张表,就简单放一下测试语句

    5.7 Distinct

      去重。我们查询年龄去重的值

    var query = collection.AsQueryable() 
                    .Select(p => new { p.Age }) 
                    .Distinct();
    

      结果如下

     

    5.8 其他

      请自行参照官方文档,官方文档网址:https://docs.mongodb.com/v3.4/reference/operator/query/

    6 c#操作Mongo查询

    6.1 插入表结构

      新建类

    class BsonDocument 
    { 
        public ObjectId _id { get; set; }
        public string Item { get; set; }
        public int Num { get; set; } 
        public List<ArrayDocument> Instock { get; set; } 
    }
    
    public class ArrayDocument
    {
        public string WareHouse { get; set; }
        public string Qty { get; set; }
    }
    

      插入数据库

    var documents = new[] { new BsonDocument{ Item="journal", Num=15, Instock=new List<ArrayDocument>(){ new ArrayDocument { WareHouse = "A", Qty = "5" }, new ArrayDocument { WareHouse = "C", Qty = "15" } } }, new BsonDocument{ Item="notebook", Num=5, Instock=new List<ArrayDocument>(){ new ArrayDocument { WareHouse = "C", Qty = "5" } } }, new BsonDocument{ Item="paper", Num=30, Instock=new List<ArrayDocument>(){ new ArrayDocument { WareHouse = "A", Qty = "60" }, new ArrayDocument { WareHouse = "B", Qty = "15" } } } , new BsonDocument{ Item="planner", Num=22, Instock=new List<ArrayDocument>(){ new ArrayDocument { WareHouse = "A", Qty = "40" }, new ArrayDocument { WareHouse = "B", Qty = "5" } } }, new BsonDocument{ Item="postcard", Num=2, Instock=new List<ArrayDocument>(){ new ArrayDocument { WareHouse = "B", Qty = "15" }, new ArrayDocument { WareHouse = "C", Qty = "35" } } } };
    
    collection.InsertMany(documents);
    

      

    6.2 普通查询

    6.2.1 查询指定item的值

      代码

    var filter = Builders<BsonDocument>.Filter.Eq("Item", "paper"); 
    var result = collection.Find(filter).ToList();
    

      结果

     

    6.2.2 查询Num值大于1的

      代码

    var filter = Builders<BsonDocument>.Filter.Gt("Num", 1); 
    var result = collection.Find(filter).ToList();
    

      结果

     

    6.2.3 and多条件查询

      代码

    //创建过滤器生成器对象 
    FilterDefinitionBuilder<BsonDocument> filterBuilder = Builders<BsonDocument>.Filter;
     //创建过滤器 
    var filter = Builders<BsonDocument>.Filter.And(filterBuilder.Gt("Num", 1), filterBuilder.Eq("Item", "notebook")); 
    var result = collection.Find(filter).ToList();
    

      结果

     

    6.2.4 or多条件查询

      代码

    //创建过滤器生成器对象 
    FilterDefinitionBuilder<BsonDocument> filterBuilder = Builders<BsonDocument>.Filter; 
    //创建过滤器 
    var filter = Builders<BsonDocument>.Filter.Or(filterBuilder.Gt("Num", 5), filterBuilder.Eq("Item", "notebook")); 
    var result = collection.Find(filter).ToList();
    

      结果

     

    6.2.5 not查询

      查找num小于10

      代码

    //创建过滤器生成器对象
    FilterDefinitionBuilder<BsonDocument> filterBuilder = Builders<BsonDocument>.Filter;
    //创建过滤器
    var filter = Builders<BsonDocument>.Filter.Not(filterBuilder.Gt("Num", 10));
    var result = collection.Find(filter).ToList();
    

      结果

     

    6.2.6 排序

      代码

    //排序规则   Ascending 正序  Descending 倒序
    SortDefinition<BsonDocument> sort = Builders<BsonDocument>.Sort.Descending("Num");
    var result = collection.Find(Builders<BsonDocument>.Filter.Empty).Sort(sort).ToList();
    

      结果

     

      

    6.2.6 in查询

      代码

    var filter = Builders<BsonDocument>.Filter.In("Item", new[] { "journal", "notebook" });
    var result = collection.Find(filter).ToList();
    

      结果

     

    6.2.6 Not In 查询

      代码

    var filter = Builders<BsonDocument>.Filter.Nin("Item", new[] { "journal", "notebook" });
    var result = collection.Find(filter).ToList();
    

      结果

     

    6.2.7 分页查询

      代码

    //Skip跳过多少页  Limit 获取多少页
    var result = collection.Find(Builders<BsonDocument>.Filter.Empty).Skip(1).Limit(1).ToList();
    

      结果

     

    6.2.8 查询总记录数

      代码

    var result = collection.Find(Builders<BsonDocument>.Filter.Empty).Count();
    

      结果

     

    6.2.9 查询指定属性

      代码

    ProjectionDefinition<BsonDocument> projection = Builders<BsonDocument>.Projection.Include("Item").Exclude("_id");
    var result = collection.Find(Builders<BsonDocument>.Filter.Empty).Project(projection).ToList();
    

      结果

     

    6.3 嵌套查询

    6.3.1 条件为嵌套文档字段时加“.

      代码

    var filter = Builders<BsonDocument>.Filter.Eq("Instock.WareHouse", "B");
    var result = collection.Find(filter).ToList();
    

      结果

     

    6.3.2 嵌套文档数组元素与指定条件匹配的所有文档   

      顺序必须一致

      代码

    var filter = Builders<BsonDocument>.Filter.AnyEq("Instock", new ArrayDocument { WareHouse="A" ,Qty="5" });
    var result = collection.Find(filter).ToList();
    

      结果

     

    6.3.3 嵌套文档数组中符合其中一个条件的查询

      代码

    var filter = Builders<BsonDocument>.Filter.Gt("Instock.0.Qty", 15);
    var result = collection.Find(filter).ToList();
    

      结果

     

      

    6.3.4 指定嵌套文档数组索引的元素条件

      代码

    var filter = Builders<BsonDocument>.Filter.Gt("Instock.0.Qty", 15);
    var result = collection.Find(filter).ToList();
    

      结果同上

    6.3.5 $ElemMatch查询

    嵌套文档数组中至少有一个满足条件

    代码 

    //创建过滤器生成器对象
    FilterDefinitionBuilder<BsonDocument> filterBuilder = Builders<BsonDocument>.Filter;
    
    //创建过滤器
    FilterDefinition<BsonDocument> filter = filterBuilder.ElemMatch<BsonDocument>("instock", new ArrayDocument{ Qty = "5", WareHouse = "A" });
    

      

    6.3.6 不使用ElemMatch的多条件查询,  只要文档数组中满足即可

    代码

    //创建过滤器生成器对象
    FilterDefinitionBuilder<BsonDocument> filterBuilder = Builders<BsonDocument>.Filter;
    
    //创建过滤器
    FilterDefinition<BsonDocument> filter = filterBuilder.And(filterBuilder.Eq("Instock.Qty",5),filterBuilder.Eq("Instock.WareHouse", "A"));
    
    var result = collection.Find(filter).ToList();
    

       

    6.3.7 查询嵌套文档中符合要求的嵌套文档数据  

      使用BsonDocument (奇葩使用)

    ProjectionDefinition<BsonDocument> projection = Builders<BsonDocument>.Projection.Include("instock").Exclude("_id");
    
    //unwind  展开数组    AppendStage 添加聚合条件    
    var result = coll.Aggregate().Unwind("instock").AppendStage<BsonDocument>(new BsonDocument { { "$match", new BsonDocument("instock.qty", new BsonDocument("$gt", 30)) } }
    ).Project(projection).ToList();
    

      使用强模型  mongo会将decimal类型变成字符串存储 ,所以不可使用decimal类型

      准备数据

    IList<User> users = new List<User>
    {
        new User
        {
            ID = "1",
            Name = "狗娃",
            Age = 11,
            Order = new List<Order>
            {
                new Order{Name="订单1",Price=111},
                new Order{Name="订单2",Price=222},
                new Order{Name="订单3",Price=333},
            }
        },
        new User
        {
            ID = "2",
            Name = "铁蛋",
            Age = 11,
            Order = new List<Order>
            {
                new Order{Name="订单4",Price=666},
                new Order{Name="订单5",Price=454},
                new Order{Name="订单6",Price=87},
            }
        },
        new User
        {
            ID = "3",
            Name = "狗剩",
            Age = 11,
            Order = new List<Order>
            {
                new Order{Name="订单7",Price=1},
                new Order{Name="订单8",Price=345},
                new Order{Name="订单9",Price=653},
            }
        }
    };
    
    //selectMany 展开子文档数组
    var res = coll.AsQueryable().SelectMany(y => y.Order).Where(y=>y.Price>555).ToList();
    

    6.4 查询NULL值属性

    6.4.1 数据表

    var documents = new[]
    {
        new BsonDocument { { "_id", 1 }, { "item", BsonNull.Value } },
        new BsonDocument { { "_id", 2 } }
    };
    
    var documents = new[] {
                    new BsonDocument {
                        Item = null
                    },
                    new BsonDocument {
                    }
                };
    collection.InsertMany(documents);
    

    6.4.2 查询值为null或者不存在的数据

      代码

    var filter = Builders<BsonDocument>.Filter.Eq("Item", BsonNull.Value);
    var result = collection.Find(filter).ToList();
    

       

    6.4.3 查询值为null的数据

      代码

    var filter = Builders<BsonDocument>.Filter.Where(u=>u.Item==null);           
    var result = collection.Find(filter).ToList();

      结果

     

    6.4.4 存在检查/查询不存在/存在此属性的值

      代码

    var filter = Builders<BsonDocument>.Filter.Exists("Item",false);            
    var result = collection.Find(filter).ToList();
    

      

     

     

  • 相关阅读:
    [转载]辗转相除法
    [转载]自由不是什么
    [翻译]与比尔·盖茨面对面
    [翻译]AJAX XMLHttpRequest对象 详解
    [转载]Win32应用程序中进程间通信方法分析与比较
    C# 中的类型转换
    Log4Net
    抽象类和接口
    有用的自定义pagecounter控件
    单点登陆单web应用的单点登陆
  • 原文地址:https://www.cnblogs.com/Lvkang/p/13974880.html
Copyright © 2020-2023  润新知