//读二进制数据的函数
BOOL OpenBinDataFile(BYTE **pBUf,UINT &len)
{
    if (pBUf == NULL)
    {
        return FALSE;
    }

    std::ifstream fs;
    fs.open(g_szBinDataPath,ios::binary);
    if (!fs.is_open())
    {
        cout<<"File:"<<g_szBinDataPath<<"not Open"<<endl;
        return FALSE;
    }

    fs.seekg(0,ios::end);
    len = fs.tellg();
    fs.seekg(0,ios::beg);

    *pBUf = new BYTE[len];
    if (NULL == *pBUf)
    {
        cout<<"内存分配不足"<<endl;
        return FALSE;
    }

    fs.read((char*)(*pBUf),len);

    fs.close();
    return TRUE;

}

//#define _USE_TRANSACTION //是否使用事务
#define _DB_TABLE_COUNTS 10 //100张表
#define LOOPSCOUNT 20 //记录数
#define TABLEFLAG 10 //第十张表写入1000个记录
#define RESETEST
BOOL SqlitePerfWithUnicode()//Unicode
{

    cout<<"UNICODE TEST:"<<endl;

    BYTE *pBuf=NULL;
    UINT len = 0;
    if (!OpenBinDataFile(&pBuf,len))
    {
        cout<<"打开二进制数据失败"<<endl;
        if (pBuf)
        {
            delete []pBuf;
        }
        return FALSE;
    }

    sqlite3 *db = NULL;
    TCHAR *errMsg = NULL;
    sqlite3_stmt *pstmt=NULL;
    TCHAR *psql = NULL;

    int nRet = -1,nRows=-1;
    nRet = sqlite3_open16(L"F:\\UnicodeTest.db",&db);
    if (nRet)
    {
        wcout<<L"无法打开UnicodeTest数据库:"<<sqlite3_errmsg16(db)<<endl;
        //sqlite3_free(errMsg);
        sqlite3_close(db);
        cin.get();

        return 1;
    }
    else
    {
        wcout<<L"成功打开UnicodeTest.db"<<endl;

    }

    TCHAR szNum[100]={0};
    TCHAR table[100]={0};
    //std::vector<std::wstring> vecTableNames;
    std::vector<std::wstring> vecID;
    std::wstring wst;

    std::vector<std::wstring> vecInsertStr,vecReadStr;
    vecInsertStr.reserve(_DB_TABLE_COUNTS);
    vecReadStr.reserve(_DB_TABLE_COUNTS);

    for (int j=0;j<LOOPSCOUNT*10;++j)
    {
        _itot(j,szNum,10);
        vecID.push_back(szNum);
    }
    for (int i=0;i<_DB_TABLE_COUNTS;++i)//建立100张表
    {
        _itot(i,szNum,10);
        //vecID.push_back(szNum);//不够
        wst = L"unicodetest_";
        wst += szNum;//表命名:unicodetest_x
        //vecTableNames.push_back(wst);
        psql = L"create table if not exists %s(id nchar(20) primary key,name blob)";
        _snwprintf_s(table,_countof(table),_TRUNCATE,psql,wst.c_str());
        //创建 _DB_TABLE_COUNTS 张表
        psql = table;
        sqlite3_prepare16(db,psql,-1,&pstmt,NULL);
        sqlite3_step(pstmt);
        sqlite3_reset(pstmt);

        psql = L"insert into %s values(?,?);";
        _snwprintf_s(table,_countof(table),_TRUNCATE,psql,wst.c_str());
        //psql = table;
        vecInsertStr.push_back(table);

        psql = L"select id,name from %s;";
        _snwprintf_s(table,_countof(table),_TRUNCATE,psql,wst.c_str());
        //psql = table;
        vecReadStr.push_back(table);

    }
   
   

    //psql = L"create table if not exists unicodetest(id nchar(20) primary key,name blob)";
    //sqlite3_prepare16(db,psql,-1,&pstmt,NULL);
    //sqlite3_step(pstmt);
    //sqlite3_reset(pstmt);
   

    DWORD dwBegin = GetTickCount();
#ifdef _USE_TRANSACTION
    sqlite3_exec(db,"begin transaction;",NULL,NULL,NULL);
#endif
    for(int j=1;j<_DB_TABLE_COUNTS;++j)
    {
        psql = const_cast<TCHAR*>(vecInsertStr[j].c_str());
#ifdef RESETEST
        sqlite3_prepare16(db,psql,-1,&pstmt,NULL);
#endif
        for (int i=0;i<LOOPSCOUNT;++i)//写
        {
#ifndef RESETEST
            sqlite3_prepare16(db,psql,-1,&pstmt,NULL);
#endif
           
            sqlite3_bind_text16(pstmt,1,vecID[i].c_str(),-1,NULL);
            sqlite3_bind_blob(pstmt,2,pBuf,len,NULL);
            sqlite3_step(pstmt);
#ifdef RESETEST
            sqlite3_reset(pstmt);
#else
            sqlite3_finalize(pstmt);
#endif

                   
        }

    }

    psql = const_cast<TCHAR*>(vecInsertStr[0].c_str());//id为"0"的表写入1000个记录
    for (int i=0;i<LOOPSCOUNT*10;++i)//写
    {
        sqlite3_prepare16(db,psql,-1,&pstmt,NULL);
        sqlite3_bind_text16(pstmt,1,vecID[i].c_str(),-1,NULL);//这里也相应的扩大
        sqlite3_bind_blob(pstmt,2,pBuf,len,NULL);
        sqlite3_step(pstmt);

        sqlite3_reset(pstmt);       
    }

#ifdef _USE_TRANSACTION
    sqlite3_exec(db,"commit transaction;",NULL,NULL,NULL);
#endif
    DWORD dwEnd = GetTickCount();

    cout<<"共有 "<< _DB_TABLE_COUNTS <<" 张表,每张表"<<"插入 "<<LOOPSCOUNT<<" 份记录(每份大小["<<len<<"B].)"<<endl;       
    cout<<"其中最后一张表插入"<<LOOPSCOUNT*10<<"记录"<<endl;
    cout<<"总耗时:"<<dwEnd-dwBegin<<endl;

   
    dwBegin = GetTickCount();
#ifdef _USE_TRANSACTION
    sqlite3_exec(db,"begin transaction;",NULL,NULL,NULL);
#endif
    for (int i=0;i<_DB_TABLE_COUNTS;++i)//读
    {       
        sqlite3_prepare16(db,vecReadStr[i].c_str(),-1,&pstmt,NULL);
        nRet = sqlite3_step(pstmt);
        while(nRet == SQLITE_ROW)
        {
            sqlite3_column_text16(pstmt,0);
            sqlite3_column_blob(pstmt,1);//数据先不读出
            nRet = sqlite3_step(pstmt);
        }
        sqlite3_reset(pstmt);
    }
#ifdef _USE_TRANSACTION
    sqlite3_exec(db,"commit transaction;",NULL,NULL,NULL);
#endif
    dwEnd = GetTickCount();

    cout<<"依次读 "<<_DB_TABLE_COUNTS<<" 张表内的 "<<LOOPSCOUNT<<"份记录,总耗时:"<<dwEnd-dwBegin<<endl;

    sqlite3_reset(pstmt);   
    sqlite3_finalize(pstmt);
    sqlite3_close(db);
    if (pBuf)
    {
        delete []pBuf;
    }

    //cin.get();
    return TRUE;

}

SQLite入门(二)读写二进制数据的更多相关文章

  1. IO流-文本IO\读写二进制数据

    文本IO 一.简述 OutputStreamWriter类使用选定的编码方式吧Unicode字符流转换为字节流,InputStreamReader类将包含字节的输入流转为可以产生Unicode字符的读 ...

  2. DevExpress XtraReports 入门二 创建 data-aware(数据感知) 报表

    原文:DevExpress XtraReports 入门二 创建 data-aware(数据感知) 报表 本文只是为了帮助初次接触或是需要DevExpress XtraReports报表的人群使用的, ...

  3. 背水一战 Windows 10 (89) - 文件系统: 读写文本数据, 读写二进制数据, 读写流数据

    [源码下载] 背水一战 Windows 10 (89) - 文件系统: 读写文本数据, 读写二进制数据, 读写流数据 作者:webabcd 介绍背水一战 Windows 10 之 文件系统 读写文本数 ...

  4. Java读写二进制数据

    import java.io.*; import java.time.LocalDate; public class Test { public static void main(String[] a ...

  5. echart图表控件配置入门(二)常用图表数据动态绑定

    上一节 <echart图表控件配置入门(一)>介绍了echarts图表控件的入门配置,使开发人员可以快速搭建出一个静态的图表.但是在实际开发过程这还是不够的,不可能所有的图表控件都是静态数 ...

  6. Qt里怎么处理二进制数据

    Qt里有个专门的类QDataStream就是专门读写二进制数据的, 它与QByteArray搭配在网络编程中有奇效. 来个栗子: // write data QByteArray data; QDat ...

  7. 重新想象 Windows 8 Store Apps (23) - 文件系统: 文本的读写, 二进制的读写, 流的读写, 最近访问列表和未来访问列表

    原文:重新想象 Windows 8 Store Apps (23) - 文件系统: 文本的读写, 二进制的读写, 流的读写, 最近访问列表和未来访问列表 [源码下载] 重新想象 Windows 8 S ...

  8. SQLite 入门教程(二)创建、修改、删除表 (转)

    转于 SQLite 入门教程(二)创建.修改.删除表 一.数据库定义语言 DDL 在关系型数据库中,数据库中的表 Table.视图 View.索引 Index.关系 Relationship 和触发器 ...

  9. SQLite入门与分析(二)---设计与概念(续)

    SQLite入门与分析(二)---设计与概念(续)   写在前面:本节讨论事务,事务是DBMS最核心的技术之一.在计算机科学史上,有三位科学家因在数据库领域的成就而获ACM图灵奖,而其中之一Jim G ...

随机推荐

  1. CentOS&.NET Core初试-1-CentOS的安装和网卡的配置

    系列目录 CentOS的安装和网卡的配置 安装.NET Core SDK和发布网站 Nginx的安装和配置 安装守护服务(Supervisor) 软件环境 系统版本:CentOS Linux rele ...

  2. ASP.NET Core中Middleware的使用

    https://www.cnblogs.com/shenba/p/6361311.html   ASP.NET 5中Middleware的基本用法 在ASP.NET 5里面引入了OWIN的概念,大致意 ...

  3. iOS开发苹果内购的介绍与实现

    1.iOS开发苹果内购的介绍 1.1 介绍 苹果规定,凡是虚拟的物品(例如:QQ音乐的乐币)进行交易时,都必须走苹果的内购通道,苹果要收取大约30%的抽成,所以不允许接入第三方的支付方式(微信.支付宝 ...

  4. C++标准库类模板(stack)和 队列(queue)

    在C++标准库(STL)中有栈和队列的类模板,因此可以直接使用 1.栈(stack):使用栈之前,要先包含头文件 : #include<stack> stack.push(elem); / ...

  5. gVim安装vim-template插件后提示Undefined variable vim_template_subtype/Press ENTER or type command to continue

    Win7 64位 gVim:version 8.1.1234 vim-template:github链接 安装方式: 直接下载master的zip压缩包,解压后放入本地gVim安装目录的plugin, ...

  6. revit 学习园地

    https://www.cnblogs.com/greatverve/category/286724.html

  7. 【javascript/css】Javascript+Css实现图片滑动浏览效果

    今天用js+css来做一个能够左右滑动的图片浏览效果. 首先写一个结构,包括需要浏览的两张图,以及能够点击来滑动图片的两个按钮. <!DOCTYPE html> <html> ...

  8. MSSqlServer 数据库降级及数据转移

    --MSSqlServer数据库降级及数据转移--MS SQL SERVER高版本数据库(Database_A)恢复数据到低版本数据库(Database_B)中--1.数据库结构对象(包含表.视图.函 ...

  9. sql 递归 STUFF

    select distinct fm_id, ,,'') AS SO_Nums from [dbo].[t_BADItems] its 表内一对多 的关系查询

  10. 理解Xaml标记语言

    理解XAML XAML基于XAML,因而具有与XAML相似的特性.在XAMl中,同样必须区分大小写,但是Xaml以.xaml作为扩展名,表示这是一个应用程序的标记扩展文件.WPF中的XAML主要用于创 ...