1、Memcached簡介數據庫
Memcached 是一個高性能的分佈式內存對象緩存系統,用於動態Web應用以減輕數據庫負載。它經過在內存中緩存數據和對象來減小讀取數據庫的次數,從而提升動態、數據庫驅動網站的速度。Memcached基於一個存儲鍵/值對的hashmap。其守護進程(daemon )是用C寫的,可是客戶端能夠用任何語言來編寫,並經過memcached協議與守護進程通訊。windows
目前有多種平臺的Memcached版本,好比Linux、FreeBSD、Solaris 、Mac OS X及Windows平臺。緩存
可在官網下載到最新版本: http://memcached.org/ (LINUX) 。安全
這裏,官網上好像沒有找到Memcached for windows
咱們安裝Windows版原本演示。socket
32bit:下載 memcached-win32-1.4.4-14.zip分佈式
64bit:若是須要win64版,下載 memcached-win64-1.4.4-14.zipmemcached
2、安裝和啓動函數
首先,我解壓文件路徑
D:\Memcached\Memcached32性能
安裝命令
以管理員身份運行 cmd.exe網站
進入到解壓文件
D:\>cd Memcached\Memcached32
安裝
D:\Memcached\Memcached32>memcached.exe -d install
啓動
D:\Memcached\Memcached32>memcached.exe -d start
OK,命令我們已經執行完了.怎麼才知道Memcached服務已經安裝成功並啓動了呢?
cmd 命令 services.msc
有時候,爲了方便起見,咱們也不能每次安裝,中止和啓動服務的時候都打開cmd命令框吧
常見的辦法是作成批處理命令,以下:
install.bat
memcached.exe -d install
start.bat
memcached.exe -d start
stop.bat
memcached.exe -d stop
unInstall.bat
memcached.exe -d uninstall
3、.net 項目中使用
筆者查閱了相關資料,發現有不少支持Memcached的客戶端,這裏因爲筆者的我的喜愛,
選擇了EnyimMemcached.2.13
能夠經過Nuget安裝
PM> Install-Package EnyimMemcached
筆者特地作了一個Demo來體驗一下,EnyimMemcached使用
首先,咱們要鏈接到這個分佈式數據庫服務,相似之前的關係型數據庫,這裏也是須要配置鏈接的,配置以下
<?xml version="1.0" encoding="utf-8" ?> <configuration> <configSections> <sectionGroup name="enyim.com"> <section name="memcached" type="Enyim.Caching.Configuration.MemcachedClientSection,Enyim.Caching" /> </sectionGroup> <section name="memcached" type="Enyim.Caching.Configuration.MemcachedClientSection, Enyim.Caching"/> </configSections> <enyim.com> <memcached> <servers> <!-- put your own server(s) here--> <add address="127.0.0.1" port="11211" /> </servers> <socketPool minPoolSize="10" maxPoolSize="100" connectionTimeout="00:00:10" deadTimeout="00:02:00" /> </memcached> </enyim.com> <memcached keyTransformer="Enyim.Caching.TigerHashTransformer,Enyim.Caching"> <servers> <add address="127.0.0.1" port="11211" /> </servers> <socketPool minPoolSize="2" maxPoolSize="100" connectionTimeout="00:00:10" deadTimeout="00:02:00" /> </memcached> <startup> <supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.5" /> </startup> </configuration>
爲了方便使用,能夠再封裝一下,便於調用,
using Enyim.Caching; using Enyim.Caching.Configuration; using Enyim.Caching.Memcached; using System; using System.Collections.Generic; using System.Linq; using System.Net; using System.Net.Sockets; using System.Text; using System.Threading.Tasks; namespace MemcachdDemo.Helper { public sealed class MemCachedHelper { private static MemcachedClient MemClient; static readonly object padlock = new object(); //線程安全的單例模式 public static MemcachedClient getInstance() { if (MemClient == null) { lock (padlock) { if (MemClient == null) { MemClientInit(); } } } return MemClient; } static void MemClientInit() { try { MemClient = new MemcachedClient(); /*MemcachedClientConfiguration config = new MemcachedClientConfiguration(); config.Servers.Add(new System.Net.IPEndPoint(IPAddress.Parse("127.0.0.1"), 11211)); config.Protocol = MemcachedProtocol.Binary; //config.Authentication.Type = typeof(PlainTextAuthenticator); //config.Authentication.Parameters["userName"] = "memcache"; //config.Authentication.Parameters["password"] = "password"; MemClient = new MemcachedClient(config);*/ /*MemcachedClientConfiguration config = new MemcachedClientConfiguration(); //config.Servers.Add(new IPEndPoint("127.0.0.1", 11211)); config.Servers.Add(new System.Net.IPEndPoint(IPAddress.Parse("127.0.0.1"), 11211)); config.Protocol = MemcachedProtocol.Binary; config.Authentication.Type = typeof(PlainTextAuthenticator); config.Authentication.Parameters["userName"] = "username"; config.Authentication.Parameters["password"] = "password"; config.Authentication.Parameters["zone"] = ""; MemClient = new MemcachedClient(config);*/ } catch (Exception ex) { throw ex; } } #region getAllKeys public static List<string> GetAllKeys(string ipString, int port) { List<string> allKeys = new List<string>(); //var ipString = "127.0.0.1"; //var port = 11211; var socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp); socket.Connect(new IPEndPoint(IPAddress.Parse(ipString), port)); var slabIdIter = QuerySlabId(socket); var keyIter = QueryKeys(socket, slabIdIter); socket.Close(); foreach (String key in keyIter) { if (!allKeys.Contains(key)) allKeys.Add(key); } return allKeys; } /// <summary> /// 執行返回字符串標量 /// </summary> /// <param name="socket">套接字</param> /// <param name="command">命令</param> /// <returns>執行結果</returns> static String ExecuteScalarAsString(Socket socket, String command) { var sendNumOfBytes = socket.Send(Encoding.UTF8.GetBytes(command)); var bufferSize = 0x1000; var buffer = new Byte[bufferSize]; var readNumOfBytes = 0; var sb = new StringBuilder(); while (true) { readNumOfBytes = socket.Receive(buffer); sb.Append(Encoding.UTF8.GetString(buffer)); if (readNumOfBytes < bufferSize) break; } return sb.ToString(); } /// <summary> /// 查詢slabId /// </summary> /// <param name="socket">套接字</param> /// <returns>slabId遍歷器</returns> static IEnumerable<String> QuerySlabId(Socket socket) { var command = "stats items STAT items:0:number 0 \r\n"; var contentAsString = ExecuteScalarAsString(socket, command); return ParseStatsItems(contentAsString); } /// <summary> /// 解析STAT items返回slabId /// </summary> /// <param name="contentAsString">解析內容</param> /// <returns>slabId遍歷器</returns> static IEnumerable<String> ParseStatsItems(String contentAsString) { var slabIds = new List<String>(); var separator = "\r\n"; var separator2 = ':'; var items = contentAsString.Split(separator, StringSplitOptions.RemoveEmptyEntries); for (Int32 i = 0; i < items.Length; i += 4) { var itemParts = items[i].Split(separator2, StringSplitOptions.RemoveEmptyEntries); if (itemParts.Length < 3) continue; slabIds.Add(itemParts[1]); } return slabIds; } /// <summary> /// 查詢鍵 /// </summary> /// <param name="socket">套接字</param> /// <param name="slabIdIter">被查詢slabId</param> /// <returns>鍵遍歷器</returns> static IEnumerable<String> QueryKeys(Socket socket, IEnumerable<String> slabIdIter) { var keys = new List<String>(); var cmdFmt = "stats cachedump {0} 200000 ITEM views.decorators.cache.cache_header..cc7d9 [6 b; 1256056128 s] \r\n"; var contentAsString = String.Empty; foreach (String slabId in slabIdIter) { contentAsString = ExecuteScalarAsString(socket, String.Format(cmdFmt, slabId)); keys.AddRange(ParseKeys(contentAsString)); } return keys; } /// <summary> /// 解析stats cachedump返回鍵 /// </summary> /// <param name="contentAsString">解析內容</param> /// <returns>鍵遍歷器</returns> static IEnumerable<String> ParseKeys(String contentAsString) { var keys = new List<String>(); var separator = "\r\n"; var separator2 = ' '; var prefix = "ITEM"; var items = contentAsString.Split(separator, StringSplitOptions.RemoveEmptyEntries); foreach (var item in items) { var itemParts = item.Split(separator2, StringSplitOptions.RemoveEmptyEntries); if ((itemParts.Length < 3) || !String.Equals(itemParts.FirstOrDefault(), prefix, StringComparison.OrdinalIgnoreCase)) continue; keys.Add(itemParts[1]); } return keys; } } /// <summary> /// String擴展函數 /// </summary> static class StringExtension { /// <summary> /// 切割 /// </summary> /// <param name="str">字符串</param> /// <param name="separator">分隔符</param> /// <param name="options">選項</param> /// <returns>切割結果</returns> public static String[] Split(this String str, Char separator, StringSplitOptions options) { return str.Split(new Char[] { separator }, options); } /// <summary> /// 切割 /// </summary> /// <param name="str">字符串</param> /// <param name="separator">分隔符</param> /// <param name="options">選項</param> /// <returns>切割結果</returns> public static String[] Split(this String str, String separator, StringSplitOptions options) { return str.Split(new String[] { separator }, options); } #endregion } }
由於EnyimMemcached幫咱們封裝的很好,剩下的就是調用了
private void button3_Click(object sender, EventArgs e) { try { if (String.IsNullOrEmpty(this.txtKey.Text)) { MessageBox.Show("key不能爲空!"); return; } else { var key = this.txtKey.Text.Trim(); var value = this.txtValue.Text.Trim(); var bRet = client.Store(StoreMode.Set, key.Trim(), txtValue.Text.Trim()); } } catch (Exception ex) { throw ex; } }
截圖以下
因爲是key-value存儲,查詢方法:
var value = mc.Get("name");
對於Memcached的安裝,啓動和基本使用,有了簡單的介紹,但願對你有用, 有用的話,請支持一下哈!