mongodb查询数据库表里总记录数count_documents()和获取记录里面的name字段的值docView[“name“].get_utf8().value.to_string()

1.先开始写点起因,就是最近开始搞mongodb的c++开发,结果呢,光是装各种驱动就花了两天。再加上视频教程里的testmongo.cpp的代码,在新版本驱动下根本就不能运行,我就想着重写一下,功能不变,代码改一下就可以。

2.结果就是,花了我整整一天才搞出来,只能说真的好扯淡,倒不是因为有多难,主要是没有开发文档,全靠各种百度,然后百度出来的代码,也是各种错误,不停需要编译。反正我编译了很多很多次才把这个代码写完,基本上写一行就要编译一次,光是为了编译通过,就花了很久很久,好在编译完成后,基本一次运行就成功。

3.之前是做Java的,由于感到太卷,想来做c++,不得不说,c++真的很坑。写法看着就很变态,而且生态环境及其差,Linux感觉就像一个黑盒一样,你也不知道库能不能跑,各种依赖,编译完只能拜神求顺利了。除此之外,代码提示约等于没有,写代码还有找开发文档,拜托,Java从来都是直接百度就行了,c++百度出来很多都有问题,问题基本就出在开发环境,要么是linux用的版本不对,要么就是库安装的位置或者版本不对。光是解决这些,就浪费了我大量的时间。c++的开发效率真的很低,比起Java差太远了 。

4.好了,说了这么多,进入正题吧。其实就是我自己解决了几个问题,网上其他人的文档都是错的,写这个,希望看到的人,不用再像我一样,浪费太多时间了。我写这个代码,有的是各种搜搜出来的,有的是自己想出来的,反正呢,我这里是原创,别的地方是没有的,反正我没搜到。

5.嗯,贴代码了,其实就是标题写的,这两个地方需要注意,其他的,都还好,不算太难。

6.先是视频教程的老版本testmongo.cpp代码:

//g++ -o testmongo testmongo.cpp -lmongoclient -lboost_thread -lboost_filesystem -lboost_program_options -L/home/itcast/driver/boost/lib -L/home/itcast/driver/mongo/lib -I/home/itcast/driver/mongo/include -I/home/itcast/driver/boost/include
#include <iostream>   

#include "mongo/client/dbclient.h"   

char dbhost[20]="localhost"; 
using namespace mongo;
using namespace std;
void printIfAge(DBClientConnection& c, int age) {  
auto_ptr<DBClientCursor> cursor = c.query("tutorial.persons", QUERY( "age" << age ).sort("name") );  
    while( cursor->more() ) {  
        BSONObj p = cursor->next();  
        cout << p.getStringField("name") << endl;  
    }  
}  

void run() {  
    DBClientConnection c;  
    c.connect(dbhost);   
    cout << "connected ok" << endl;  
    BSONObj p = BSON( "name" << "Joe" << "age" << 33 );  
    c.insert("tutorial.persons", p); /**< 向person表中插入数据 */  
    p = BSON( "name" << "Jane" << "age" << 40 );  
    c.insert("tutorial.persons", p);  
    p = BSON( "name" << "Abe" << "age" << 33 );  
    c.insert("tutorial.persons", p);  
    p = BSON( "name" << "Samantha" << "age" << 21 << "city" << "Los Angeles" << "state" << "CA" );  
    c.insert("tutorial.persons", p);  
    c.ensureIndex("tutorial.persons", fromjson("{age:1}"));  
    cout << "count:" << c.count("tutorial.persons") << endl; /**< 显示person表中的数据数目 */  
    auto_ptr<DBClientCursor> cursor = c.query("tutorial.persons", BSONObj());  
    while( cursor->more() ) {  
        cout << cursor->next().toString() << endl;  
    }  
    cout << "\nprintifage:\n";  
    printIfAge(c, 33);  
}  
int main(int argc,char *argv[]) {  
    if(argc == 2)
    {
        memset(dbhost,0x00,sizeof(dbhost));
        strcpy(dbhost,argv[1]);
        printf("connect to dbhost:[%s]\n",dbhost);
    }
    else
    {
        printf("connect to dbhost:[%s]\n",dbhost);
        printf("if you need to connet to remote service,please input ip!\n");
    }

    try {  
        run();  
    }  

    catch( DBException &e ) {  
        cout << "caught " << e.what() << endl;  
    }  
    return 0;  
}

7.上面这个是人家视频里的老版本驱动代码,我本来也是打算这么写的,但是奈何自己的Linux一直都装驱动失败,只能装新版的驱动,新版的驱动装好了,但是代码也得重写,就很头疼。好了,上我的原创代码:TestMongoOld.cpp

#include <iostream>
#include <cstring>

#include <bsoncxx/builder/stream/document.hpp>
#include <bsoncxx/json.hpp>

#include <mongocxx/client.hpp>

//11.老版本的连接参数,很简单;新版本不加mongodb://根本编译不过去;
//char dbhost[20]="localhost"; 

char dbhost[20]="mongodb://localhost";
using namespace mongocxx;
using namespace std;

//8.老版本第一个参数是数据库连接,就在这里,也是要改的;
//void printIfAge(DBClientConnection& c, int age) { 

void printIfAge(collection& collection, int age) { 

	//9.老版本的条件查询,其实就是查询age=33的条数,同时按name进行升序排列;
	/*auto_ptr<DBClientCursor> cursor = c.query("tutorial.persons", QUERY( "age" << age ).sort("name") );  
    while( cursor->more() ) {  
        BSONObj p = cursor->next();  
		//10.这里是从json串中,通过key为name,拿到对应的value;
        cout << p.getStringField("name") << endl;  
    }*/ 
	
	//16.新版本的过滤器,也是很头疼,翻了好多文档才搞明白;
	bsoncxx::builder::stream::document document{};
	auto filter = document << "age" << age << bsoncxx::builder::stream::finalize;
	auto order = document << "name" << 1 << bsoncxx::builder::stream::finalize;
	
	options::find opts = options::find{};
	opts.sort(order.view());
	
	cursor cursor = collection.find(filter.view(), opts);
	for(bsoncxx::document::view docView : cursor) {
		//cout << bsoncxx::to_json(docView) << std::endl;
		//17.这行是新版本取name值的写法,呃,我找了好半天才搞明白,网上的教程都是错误的;
		cout << docView["name"].get_utf8().value.to_string() << std::endl;
	}

}

void run() {
	
	//2.老版本的mongodb数据库连接;
	/*DBClientConnection c;  
    c.connect(dbhost);*/
	
	//12.新版本的连接方式,我已经尽量和老版本的代码看起来一样了,总体来说,变化挺大的,但不是更简单,而是更复杂了;
	client conn{uri{dbhost}};
	cout << "connect ok" << endl;
	
	//3.老版本的mongodb插入数据,以及创建数据库,现在都不能用了,看下面的新版本吧;
	/*BSONObj p = BSON( "name" << "Joe" << "age" << 33 );  
    c.insert("tutorial.persons", p); //< 向person表中插入数据   
    p = BSON( "name" << "Jane" << "age" << 40 );  
    c.insert("tutorial.persons", p);  
    p = BSON( "name" << "Abe" << "age" << 33 );  
    c.insert("tutorial.persons", p);  
    p = BSON( "name" << "Samantha" << "age" << 21 << "city" << "Los Angeles" << "state" << "CA" );  
    c.insert("tutorial.persons", p);  
    c.ensureIndex("tutorial.persons", fromjson("{age:1}"));*/
	
	//13.新版本要插入数据,还得先创建一个文档集合,然后再创建文档,也是很要命;还是老版本的json形式好很多;
	/**< 向person表中插入数据 */
	auto collection = conn["tutorial"]["persons"];
	
	bsoncxx::builder::stream::document document1{};
	document1 << "name" << "Joe" << "age" << 33;
	collection.insert_one(document1.view());
	
	bsoncxx::builder::stream::document document2{};
	document2 << "name" << "Jane" << "age" << 40;
	collection.insert_one(document2.view());
	
	bsoncxx::builder::stream::document document3{};
	document3 << "name" << "Abe" << "age" << 33;
	collection.insert_one(document3.view());
	
	bsoncxx::builder::stream::document document4{};
	document4 << "name" << "Samantha" << "age" << 21 << "city" << "Los Angeles" << "state" << "CA";
	collection.insert_one(document4.view());
	
	//4.老版本的mongodb创建索引;
	//c.ensureIndex("tutorial.persons", fromjson("{age:1}"));
	
	//14.新版本的创建索引,真是烦,看着就头疼;
	bsoncxx::builder::stream::document document{};
	auto index_specification = document << "age" << 1 << bsoncxx::builder::stream::finalize; // 升序1,降序-1
	collection.create_index(move(index_specification));
	
	//5.老板本的输出表总条数,现在已经不能这么用了;
	//cout << "count:" << c.count("tutorial.persons") << endl; /**< 显示person表中的数据数目 */
	
	//15.新版本的统计总条数,网上查了一圈,才在stackoverflow上找到,连count()都没了,只能用count_documents(),还必须要加过滤器;
	/**< 显示person表中的数据数目 */ 
	bsoncxx::document::view empty_filter;
	cout << "count:" << collection.count_documents(empty_filter)  << endl;
	
	//6.老版本的遍历表里所有数据,总得来说,老版本的代码要简单很多;
	/*auto_ptr<DBClientCursor> cursor = c.query("tutorial.persons", BSONObj());  
    while( cursor->more() ) {  
        cout << cursor->next().toString() << endl;  
    }*/ 
	
	cursor cursor = collection.find({});
	for(bsoncxx::document::view docView : cursor) {
		std::cout << bsoncxx::to_json(docView) << std::endl;
	}
	
	cout << "\nprintifage:\n";
	
	//7.老版本的这个函数,第一个参数传的是数据库连接,新版本已经是文档集合collection了;
	//printIfAge(c, 33);
	
	printIfAge(collection, 33);

}
int main(int argc,char* argv[]) {
	if(argc == 2)
	{
		memset(dbhost,0x00,sizeof(dbhost));
		strcpy(dbhost,argv[1]);
		printf("connect to dbhost:[%s]\n",dbhost);
	}
	else
	{
		printf("connect to dbhost:[%s]\n",dbhost);
		printf("if you need to connect to remote service,please input ip!\n");
	}
	
	try {
		run();
	}
	//1.这个异常类型,在iostream里面没有,新版的mongocxx驱动里,并没有这个异常类型;
	//catch( DBException &e ) {
	catch (exception &e) {
		cout << "caught " << e.what() << endl;
	}
	return 0;
}

/**
控制台输出的结果:

connect to dbhost:[mongodb://localhost]
if you need to connect to remote service,please input ip!
connect ok
count:4
{ "_id" : { "$oid" : "62e55239de764029fc143672" }, "name" : "Joe", "age" : 33 }
{ "_id" : { "$oid" : "62e55239de764029fc143673" }, "name" : "Jane", "age" : 40 }
{ "_id" : { "$oid" : "62e55239de764029fc143674" }, "name" : "Abe", "age" : 33 }
{ "_id" : { "$oid" : "62e55239de764029fc143675" }, "name" : "Samantha", "age" : 21, "city" : "Los Angeles", "state" : "CA" }

printifage:
Abe
Joe
*/

//18.总体而言,c++就是个坑,对比Java来说,不仅文档和资料几乎没有,而且写法变化之大也是令人咋舌。我真的怀疑写c++的人,是不是都背熟了开发文档,之前写Java从来都是现场百度,对比之下,
//c++的开发效率是真的低。

8.上面的编译指令:c++ --std=c++11 TestMongo.cpp -o TestMongo.out $(pkg-config --cflags --libs libmongocxx),这个指令要是出问题,运行是出现缺少库,就把输出信息粘到百度,搜一下就可以解决。

9.总体来说,全在代码里面了。对了,我用的是uos,源换成清华的ubuntu源了。

10.感觉前面的起因写的有点多了,可能让文章搜不到,就不能帮到其他人了,我把简介里的粘过来,应该会好一些。

1.mongodb的c++连接方式;

2.mongodb插入多条数据,也就是多个文档document;

3.创建索引;

4.count_document获取总条数;

5.遍历并输出表里所有的数据;

6.根据age过滤和name排序,获取特定的数据;

7.遍历输出记录数里的name;

  • 2
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 3
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值