惯性聚合 高效追踪和阅读你感兴趣的博客、新闻、科技资讯
阅读原文 在惯性聚合中打开

推荐订阅源

C
CXSECURITY Database RSS Feed - CXSecurity.com
P
Privacy International News Feed
V
Vulnerabilities – Threatpost
The Last Watchdog
The Last Watchdog
Threat Intelligence Blog | Flashpoint
Threat Intelligence Blog | Flashpoint
Exploit-DB.com RSS Feed
Exploit-DB.com RSS Feed
O
OpenAI News
T
Threat Research - Cisco Blogs
WordPress大学
WordPress大学
OSCHINA 社区最新新闻
OSCHINA 社区最新新闻
P
Palo Alto Networks Blog
cs.AI updates on arXiv.org
cs.AI updates on arXiv.org
H
Help Net Security
P
Proofpoint News Feed
MyScale Blog
MyScale Blog
Security Archives - TechRepublic
Security Archives - TechRepublic
T
The Blog of Author Tim Ferriss
H
Hackread – Cybersecurity News, Data Breaches, AI and More
S
Securelist
Vercel News
Vercel News
S
Security Affairs
D
Darknet – Hacking Tools, Hacker News & Cyber Security
B
Blog RSS Feed
云风的 BLOG
云风的 BLOG
K
KPMG report finds enterprise disconnect between AI and its ROI | CIO
Blog — PlanetScale
Blog — PlanetScale
让小产品的独立变现更简单 - ezindie.com
让小产品的独立变现更简单 - ezindie.com
Last Week in AI
Last Week in AI
博客园_首页
Attack and Defense Labs
Attack and Defense Labs
G
Google Developers Blog
T
Tor Project blog
Project Zero
Project Zero
腾讯CDC
Schneier on Security
Schneier on Security
月光博客
月光博客
N
Netflix TechBlog - Medium
AWS News Blog
AWS News Blog
L
LINUX DO - 最新话题
P
Proofpoint News Feed
博客园 - 司徒正美
A
About on SuperTechFans
Latest news
Latest news
Scott Helme
Scott Helme
Hacker News: Ask HN
Hacker News: Ask HN
T
Threatpost
Hacker News - Newest:
Hacker News - Newest: "LLM"
C
CERT Recently Published Vulnerability Notes
Google DeepMind News
Google DeepMind News
博客园 - 聂微东

博客园 - MaxIE

jQuery选择器和选取方法 为什么Android的图片质量会比iPhone的差? 百度地图计算两坐标点之间距离计算 MS SQL SERVER索引优化相关查询 SSD在SQLServer中的应用 Speech两种使用方法 让.net程序自动运行在管理员权限下 “请求的操作无法在使用用户映射区域打开的文件上执行”问题处理 C#随机字符串随机性不足的解決方式(随机数重复) json.net处理复杂json 未在本地计算机上注册“Microsoft.Jet.OLEDB.4.0”提供程序 解决办法 excel中根据单元格背景颜色进行数据筛选(excel2003实现方法) 跨平台加密版 SQLite 3 - wxSQLite3 数据库sql2000错误8908及处理 jQuery2011年年度最佳插件 jQ中文API离线版下载(适用版本1.4.4,1.5,1.5.1,1.5.2,1.6,1.6.1,1.6.2) 方便的CSS和jQuery下拉菜单解决方案 sql2000无法执行查询及未找到提供程序解决办法 SQL Server优化SELECT语句方法
.net下BerkeleyDB操作封装C#版(附单元测试)
MaxIE · 2014-05-23 · via 博客园 - MaxIE

using System;

using System.Collections.Generic;

using System.IO;

using System.Linq;

using System.Runtime.Serialization.Formatters.Binary;

using System.Text;

using BerkeleyDb;

using Component;

namespace ToolManager
{
   public class BDBRecord
   {
       public object Key { get; set; }
       public string Value { get; set; }
   }    /**//// <summary>
   /// BDB数据库操作类库
   /// </summary>
   public class BDBHelper
   {

       private string DBFilePath { get; set; }
       private DBStoreType DBType { get; set; }
       public enum DBStoreType : byte
       {
           Auto=1,
           Queue,
           Hash
       }
       [Obsolete("该构造函数已废弃 ,请使用BDBHelper(string dbfilePath)")]
       public BDBHelper()
       {
       }

       public BDBHelper(string dbfilePath)
       {
           this.DBFilePath = dbfilePath;
       }
       [Obsolete("该构造函数已废弃 ,请使用BDBHelper(string dbfilePath)")]
       public BDBHelper(string dbfilePath, DBStoreType type)
       {
           this.DBFilePath = dbfilePath;
           this.DBType = type;
       }
       public BDBRecord FindOne()
       {
           return this.FindOne(null);
       }
       public BDBRecord FindOne(Func<object, string, bool> predicate)
       {
           //Dictionary<string, object> dict = new Dictionary<string, object>();
           try
           {
               Queue格式#region Queue格式
               //if (this.DBType == DBStoreType.Queue)
               //{
               using (Db db = new Db(DbCreateFlags.None))
               {
                   db.RecLen = 5000;
                   db.RecPad = '.';
                   DbQueue file = (DbQueue)db.Open(null, this.DBFilePath, null, DbType.Queue, Db.OpenFlags.Create, 0);
                   using (DbQueueCursor cursor = file.OpenCursor(null, DbFileCursor.CreateFlags.None))
                   {
                       foreach (KeyDataPair kvp in cursor)
                       {
                           BinaryFormatter bf = new BinaryFormatter();
                           MemoryStream stream = new MemoryStream();
                           stream.Write(kvp.Data.Buffer, 0, kvp.Data.Size);
                           stream.Seek(0, SeekOrigin.Begin);
                           string k = BitConverter.ToInt32(kvp.Key.Buffer, 0).ToString();
                           object v = bf.Deserialize(stream);
                           if (predicate == null)
                           {
                               return new BDBRecord() { Key = v, Value = k };
                           }
                           else if (predicate(v, k))
                           {
                               return new BDBRecord() { Key = v, Value = k };
                           }
                       }
                   }
               }
               //}
               #endregion
           }
           catch (Exception ex)
           {
               Hash格式#region Hash格式
               //else if(this.DBType==DBStoreType.Hash)
               //{
               //遍历数据
               using (Db db = new Db(DbCreateFlags.None))
               {
                   //这里如果应用Db.OpenFlags.Create则在启动后会覆盖同名文件,并新建同名文件
                   //Db.OpenFlags.Truncate会清空数据库
                   DbHash dbf = (DbHash)db.Open(null, this.DBFilePath, null, DbType.Hash,
       Db.OpenFlags.ThreadSafe, 0);

                   using (DbHashCursor cursor = dbf.OpenCursor(null, DbFileCursor.CreateFlags.None))
                   {
                       foreach (KeyDataPair kvp in cursor)
                       {
                           BinaryFormatter bf = new BinaryFormatter();
                           MemoryStream stream = new MemoryStream();
                           stream.Write(kvp.Data.Buffer, 0, kvp.Data.Size);
                           stream.Seek(0, SeekOrigin.Begin);
                           string k = Encoding.UTF8.GetString(kvp.Key.Buffer, 0, kvp.Key.Size);
                           object v = bf.Deserialize(stream);
                           if (predicate == null)
                           {
                               return new BDBRecord() { Key = v, Value = k };
                           }
                           else if (predicate(v, k))
                           {
                               return new BDBRecord() { Key = v, Value = k };
                           }
                       }
                   }
               }
               #endregion
               //}
           }
           //return dict;
           return null;
       }
       public Dictionary<object, string> FindAll(Func<object, string, bool> predicate)
       {

           Dictionary<object, string> dict = new Dictionary<object, string>();
           try
           {
               Queue格式#region Queue格式
               //if (this.DBType == DBStoreType.Queue)
               //{
               using (Db db = new Db(DbCreateFlags.None))
               {
                   db.RecLen = 5000;
                   db.RecPad = '.';
                   DbQueue file = (DbQueue)db.Open(null, this.DBFilePath, null, DbType.Queue, Db.OpenFlags.Create, 0);
                   using (DbQueueCursor cursor = file.OpenCursor(null, DbFileCursor.CreateFlags.None))
                   {
                       foreach (KeyDataPair kvp in cursor)
                       {
                           _Do2(kvp, predicate, dict);
                       }
                   }
               }
               //}
               #endregion
           }
           catch (Exception ex)
           {
               Hash格式#region Hash格式
               //else if(this.DBType==DBStoreType.Hash)
               //{
               //遍历数据
               using (Db db = new Db(DbCreateFlags.None))
               {
                   //这里如果应用Db.OpenFlags.Create则在启动后会覆盖同名文件,并新建同名文件
                   //Db.OpenFlags.Truncate会清空数据库
                   DbHash dbf = (DbHash)db.Open(null, this.DBFilePath, null, DbType.Hash,
       Db.OpenFlags.ThreadSafe, 0);

                   using (DbHashCursor cursor = dbf.OpenCursor(null, DbFileCursor.CreateFlags.None))
                   {
                       foreach (KeyDataPair kdp in cursor)
                       {
                           _Do(kdp, predicate, dict);
                       }
                   }
               }
               #endregion
               //}
           }
           return dict;
       }
       public Dictionary<object, string> FindAll()
       {
           //either below works fine
           //return this.FindAll((s, o) => true);
           return this.FindAll(null);
       }
       private static void _Do(KeyDataPair kvp, Func<object, string, bool> predicate, Dictionary<object, string> result)
       {
           BinaryFormatter bf = new BinaryFormatter();
           MemoryStream stream = new MemoryStream();
           stream.Write(kvp.Data.Buffer, 0, kvp.Data.Size);
           stream.Seek(0, SeekOrigin.Begin);
           string k = Encoding.UTF8.GetString(kvp.Key.Buffer, 0, kvp.Key.Size);
           object v = bf.Deserialize(stream);
           if (predicate == null)
           {
               result.Add(v, k);
           }
           else if (predicate(v, k))
           {
               result.Add(v, k);
           }
       }
       private static void _Do2(KeyDataPair kvp, Func<object, string, bool> predicate, Dictionary<object, string> result)
       {
           BinaryFormatter bf = new BinaryFormatter();
           MemoryStream stream = new MemoryStream();
           stream.Write(kvp.Data.Buffer, 0, kvp.Data.Size);
           stream.Seek(0, SeekOrigin.Begin);
           string k = BitConverter.ToInt32(kvp.Key.Buffer, 0).ToString();
           object v = bf.Deserialize(stream);
           if (predicate == null)
           {
               result.Add(v, k);
           }
           else if (predicate(v, k))
           {
               result.Add(v, k);
           }
       }
       /**//// <summary>
       /// 更新数据库中的数据
       /// </summary>
       /// <param name="predicate">execute condition</param>
       /// <param name="isMatchOnlyOnce">is match only once</param>
       /// <returns>effect records</returns>
       public int UpdateInQueueMode(Func<int, object, bool> predicate, object value,bool isMatchOnlyOnce)
       {
                int count = 0;
                if (predicate == null)
                    return 0;
              //遍历数据
               using (Db db = new Db(DbCreateFlags.None))
               {
                   db.RecLen = 5000;
                   db.RecPad = '.';
                   //这里如果应用Db.OpenFlags.Create则在启动后会覆盖同名文件,并新建同名文件
                   //Db.OpenFlags.Truncate会清空数据库
                   DbQueue dbf = (DbQueue)db.Open(null, this.DBFilePath, null, DbType.Queue,
       Db.OpenFlags.ThreadSafe|Db.OpenFlags.Create, 0);

                   using (DbQueueCursor cursor = dbf.OpenCursor(null, DbFileCursor.CreateFlags.None))
                   {
                       BinaryFormatter bf = new BinaryFormatter();
                       MemoryStream stream = new MemoryStream();
                       foreach (KeyDataPair kdp in cursor)
                       {
                           int k = BitConverter.ToInt32(kdp.Key.Buffer, 0);
                           Console.WriteLine("k={0}", k.ToString());
                           stream.SetLength(0);
                           stream.Position = 0;
                           stream.Write(kdp.Data.Buffer, 0, kdp.Data.Size);
                           stream.Seek(0, SeekOrigin.Begin);
                           object v = bf.Deserialize(stream);
                           if(predicate(k,v))
                           {
                               count++;
                               //string d = Encoding.UTF8.GetString(kdp.Data.Buffer, 0, kdp.Data.Size);
                               //如何读取Queue类型的主键值

                               //Console.WriteLine("{0},{1}", p2.State, p2.Os);
                               //p2.Os = "changed";
                               //stream = new MemoryStream();
                               stream.Position = 0;
                               stream.SetLength(0);
                               bf.Serialize(stream, value);
                               DbEntry data = DbEntry.InOut(stream.ToArray());
                               cursor.Put(ref data);
                               if (isMatchOnlyOnce)
                               {
                                   stream.Close();
                                   return count;
                               }
                           }
                       }
                           stream.Close();
                   }
           }
           return count;
       }

       public void CreateInQueueMode(object value)
       {
           Db PC = new Db(DbCreateFlags.None);
           PC.RecLen = 5000;
           PC.RecPad = '.';
           DbQueue file = (DbQueue)PC.Open(null, this.DBFilePath, null, DbType.Queue, Db.OpenFlags.Create|Db.OpenFlags.ThreadSafe, 0);
           //CreateSecondaryDB(file,"Id.PCs.s",new DbFile.KeyGeneratorFcn(Common.Id));
           //CreateSecondaryDB(file, "Id.PCs.s", new DbFile.KeyGeneratorFcn(Common.Id));
           //由于数据量不是很大,不考虑使用二级数据库,直接使用游标操作,降低复杂度
           //首先遍历数据库看有没有已经存在,如果没有,则添加一个,如果有,改变其状态
           BinaryFormatter bf = new BinaryFormatter();
           MemoryStream stream= new MemoryStream();
           bf.Serialize(stream, value);
           DbEntry k = DbEntry.Out(new byte[1024]);
           DbEntry data = DbEntry.InOut(stream.ToArray());
           file.Append(null, ref k, ref data);
           stream.Close();
           file.Sync();
           PC.Close();
       }
       public int DeleteInQueueMode(Func<int, object, bool> predicate,bool isMatchOnlyOnce)
       {
           int count = 0;
           if (predicate == null)
               return 0;
           //遍历数据
           using (Db db = new Db(DbCreateFlags.None))
           {
               db.RecLen = 5000;
               db.RecPad = '.';
               //这里如果应用Db.OpenFlags.Create则在启动后会覆盖同名文件,并新建同名文件
               //Db.OpenFlags.Truncate会清空数据库
               DbQueue dbf = (DbQueue)db.Open(null, this.DBFilePath, null, DbType.Queue,
   Db.OpenFlags.ThreadSafe|Db.OpenFlags.Create, 0);

               using (DbQueueCursor cursor = dbf.OpenCursor(null, DbFileCursor.CreateFlags.None))
               {
                   BinaryFormatter bf = new BinaryFormatter();
                   MemoryStream stream = new MemoryStream();
                   foreach (KeyDataPair kdp in cursor)
                   {
                       int k = BitConverter.ToInt32(kdp.Key.Buffer, 0);
                       Console.WriteLine("k={0}", k.ToString());
                       stream.SetLength(0);
                       stream.Position = 0;
                       stream.Write(kdp.Data.Buffer, 0, kdp.Data.Size);
                       stream.Seek(0, SeekOrigin.Begin);
                       object v = bf.Deserialize(stream);
                       if (predicate(k, v))
                       {
                           count++;
                           //string d = Encoding.UTF8.GetString(kdp.Data.Buffer, 0, kdp.Data.Size);
                           //如何读取Queue类型的主键值

                           //Console.WriteLine("{0},{1}", p2.State, p2.Os);
                           //p2.Os = "changed";
                           //stream = new MemoryStream();
                           //stream.Position = 0;
                           //stream.SetLength(0);
                           //bf.Serialize(stream, v);
                           //DbEntry data = DbEntry.InOut(stream.ToArray());
                           //cursor.Put(ref data);
                           cursor.Delete();
                           if (isMatchOnlyOnce)
                           {
                               stream.Close();
                               return count;
                           }
                       }
                   }stream.Close();
               }
           }
           return count;
       }

       /**//// <summary>
       /// 用于向支持重复键值的数据库文件添加数据
       /// </summary>
       /// <param name="key"></param>
       /// <param name="value"></param>
       public void CreateInHashModeWithDup(string key,object value)
       {
           //这里只是更新了一条记录,更新多条同key的情况没有考虑
           Db db = new Db(DbCreateFlags.None);
           db.SetFlags(DbFlags.Dup);
           DbFile dbf = db.Open(null, this.DBFilePath, null, DbType.Hash, Db.OpenFlags.Create|Db.OpenFlags.ThreadSafe, 0);
           MemoryStream stream = new MemoryStream();
           BinaryFormatter formatter = new BinaryFormatter();
           formatter.Serialize(stream, value);
           DbEntry _key = DbEntry.InOut(Encoding.UTF8.GetBytes(key));
           DbEntry _data = DbEntry.InOut(stream.ToArray());
           if (dbf.Put(null, ref _key, ref _data) != 0)
               Console.Write("{0}:输入错误", key);
           stream.Close();
           dbf.Sync();//数据更新
           db.Close();
       }
       /**//// <summary>
       /// 默认方式,如果已有键则进行更新操作
       /// </summary>
       /// <param name="key"></param>
       /// <param name="value"></param>
       public void CreateOrUpdateInHashModeWithoutDup(string key,object value)
       {
           //这里只是更新了一条记录,更新多条同key的情况没有考虑
           Db db = new Db(DbCreateFlags.None);
           //db.SetFlags(DbFlags.Dup);
           DbFile dbf = db.Open(null, this.DBFilePath, null, DbType.Hash, Db.OpenFlags.Create|Db.OpenFlags.ThreadSafe, 0);
           MemoryStream stream = new MemoryStream();
           BinaryFormatter formatter = new BinaryFormatter();
           formatter.Serialize(stream, value);
           DbEntry _key = DbEntry.InOut(Encoding.UTF8.GetBytes(key));
           DbEntry _data = DbEntry.InOut(stream.ToArray());
           if (dbf.Put(null, ref _key, ref _data) != 0)
               Console.Write("{0}:输入错误", key);
           stream.Close();
           dbf.Sync();//数据更新
           db.Close();
       }
       public int UpdateInHashMode(Func<string,object,bool> predicate,object value,bool isMatchOnlyOnce)
       {
           int count = 0;
           if (predicate == null)
               return count;
          //遍历数据
           using (Db db = new Db(DbCreateFlags.None))
           {
               //这里如果应用Db.OpenFlags.Create则在启动后会覆盖同名文件,并新建同名文件
               //Db.OpenFlags.Truncate会清空数据库
               DbHash dbf = (DbHash)db.Open(null, this.DBFilePath, null, DbType.Hash,
   Db.OpenFlags.ThreadSafe|Db.OpenFlags.Create, 0);

               using (DbHashCursor cursor = dbf.OpenCursor(null, DbFileCursor.CreateFlags.None))
               {
                   BinaryFormatter bf = new BinaryFormatter();
                   MemoryStream stream = new MemoryStream();
                  foreach (KeyDataPair kvp in cursor)
                   {
                       stream.SetLength(0);
                       stream.Position = 0;
                       stream.Write(kvp.Data.Buffer, 0, kvp.Data.Size);
                       stream.Seek(0, SeekOrigin.Begin);
                       string k = Encoding.UTF8.GetString(kvp.Key.Buffer, 0, kvp.Key.Size);
                       object v = bf.Deserialize(stream);
                       if (predicate(k, v))
                       {
                           count++;
                           stream.SetLength(0);
                           stream.Position = 0;
                           bf.Serialize(stream, value);
                           DbEntry data = DbEntry.InOut(stream.ToArray());
                           cursor.Put(ref data, DbKeyCursor<DbHashCursor, DbHash>.PutMode.Current);
                           if (isMatchOnlyOnce)
                           {
                               stream.Close();
                               return count;
                           }
                       }
                   }
                   stream.Close();
               }
           }
           return count;
       }
       public int DeleteInHashMode(Func<string,object,bool> predicate,bool isMatchOnlyOnce)
       {
           int count = 0;
           if (predicate == null)
               return count;
           //遍历数据
           using (Db db = new Db(DbCreateFlags.None))
           {
               //这里如果应用Db.OpenFlags.Create则在启动后会覆盖同名文件,并新建同名文件
               //Db.OpenFlags.Truncate会清空数据库
               DbHash dbf = (DbHash)db.Open(null, this.DBFilePath, null, DbType.Hash,
   Db.OpenFlags.ThreadSafe|Db.OpenFlags.Create, 0);

               using (DbHashCursor cursor = dbf.OpenCursor(null, DbFileCursor.CreateFlags.None))
               {
                   BinaryFormatter bf = new BinaryFormatter();
                   MemoryStream stream = new MemoryStream();
                   foreach (KeyDataPair kvp in cursor)
                   {
                       stream.SetLength(0);
                       stream.Position = 0;
                       stream.Write(kvp.Data.Buffer, 0, kvp.Data.Size);
                       stream.Seek(0, SeekOrigin.Begin);
                       string k = Encoding.UTF8.GetString(kvp.Key.Buffer, 0, kvp.Key.Size);
                       object v = bf.Deserialize(stream);
                       if (predicate(k, v))
                       {
                           count++;
                           cursor.Delete();
                           if (isMatchOnlyOnce)
                           {
                               stream.Close();
                               return count;
                           }
                       }
                   }
                   stream.Close();
               }
           }
           return count;
       }
   }
}