一、首先大致介绍下蓝牙4.0的模式,中心和周边:

一般情况下,iPhone作为中心,接收来自周边传感器(比如手环等)采集的数据。

二、那整一个数据通讯的协议是怎样的呢?

为什么要一层层搞这么复杂呢?据我的理解是这样的:

  (1)蓝牙2.0的通讯非常简单,只有数据接收和发送,这样产生的问题就是:假如我有2个传感器的数据,但传输通道就一个,就发送时必须自己切割字符串等。

      但4.0根据不同的功能,有点像传输分了很多“通道”,比如传感器1传输温度,服务的UUID是FFF0,然后特征字节发送的UUID为FFF1;传感器2传输距离,服务的UUID也是FFF0,但是特征字节发送的UUID为FFF2,这样就可以各取所需了,而不是蓝牙2.0那样一股脑儿收进来再切割。

  (2)蓝牙4.0的每个“通道”都可以定义为发送或者接收字节,所以可以把发送和接收区分开。

  补充:一般情况下,服务(Service)的UUID根据功能来区分(假如有FFF0和FFFE0两种服务),比如FFF0的服务ID里的特征字节UUID通道用来作为传感器通讯,FFE0里放蓝牙设备的信息,名称啊电池啊等等。。

三、代码:

1.BLEInfo.h(存放周边蓝牙设备的信息)

  1. #import <Foundation/Foundation.h>
  2. #import <CoreBluetooth/CoreBluetooth.h>
  3. @interface BLEInfo : NSObject
  4.  
  5. @property (nonatomic, strong) CBPeripheral *discoveredPeripheral;
  6. @property (nonatomic, strong) NSNumber *rssi;
  7.  
  8. @end

BLEInfo.m

  1. #import "BLEInfo.h"
  2.  
  3. @implementation BLEInfo
  4.  
  5. @end

2.RootTableViewController.h(显示周边蓝牙信息,主要用scan函数就行了)

  1. #import <UIKit/UIKit.h>
  2. #import <CoreBluetooth/CoreBluetooth.h>
  3. #import "BLEInfo.h"
  4. #import "DetailViewController.h"
  5. @interface RootTableViewController : UITableViewController<CBCentralManagerDelegate>
  6.  
  7. @property (nonatomic, strong) CBCentralManager *centralMgr;
  8. @property (nonatomic, strong) NSMutableArray *arrayBLE;
  9.  
  10. @end

RootTableViewController.m

  1. #import "RootTableViewController.h"
  2.  
  3. @interface RootTableViewController ()
  4.  
  5. @end
  6.  
  7. @implementation RootTableViewController
  8.  
  9. - (void)viewDidLoad {
  10. [super viewDidLoad];
  11. self.navigationItem.title=@"蓝牙搜索";
  12. self.centralMgr = [[CBCentralManager alloc] initWithDelegate:self queue:nil];
  13. self.arrayBLE = [[NSMutableArray alloc] init];
  14. }
  15.  
  16. - (void)didReceiveMemoryWarning {
  17. [super didReceiveMemoryWarning];
  18. // Dispose of any resources that can be recreated.
  19. }
  20.  
  21. //蓝牙状态delegate
  22. - (void)centralManagerDidUpdateState:(CBCentralManager *)central
  23. {
  24. switch (central.state)
  25. {
  26. case CBCentralManagerStatePoweredOn:
  27. [self.centralMgr scanForPeripheralsWithServices:nil options:nil];
  28. NSLog(@"start scan Peripherals");
  29.  
  30. break;
  31.  
  32. default:
  33. NSLog(@"Central Manager did change state");
  34. break;
  35. }
  36. }
  37.  
  38. //发现设备delegate
  39. - (void)centralManager:(CBCentralManager *)central didDiscoverPeripheral:(CBPeripheral *)peripheral advertisementData:(NSDictionary *)advertisementData RSSI:(NSNumber *)RSSI
  40. {
  41. BLEInfo *discoveredBLEInfo = [[BLEInfo alloc] init];
  42. discoveredBLEInfo.discoveredPeripheral = peripheral;
  43. discoveredBLEInfo.rssi = RSSI;
  44.  
  45. // update tableview
  46. [self saveBLE:discoveredBLEInfo];
  47.  
  48. }
  49.  
  50. //保存设备信息
  51. - (BOOL)saveBLE:(BLEInfo *)discoveredBLEInfo
  52. {
  53. for (BLEInfo *info in self.arrayBLE)
  54. {
  55. if ([info.discoveredPeripheral.identifier.UUIDString isEqualToString:discoveredBLEInfo.discoveredPeripheral.identifier.UUIDString])
  56. {
  57. return NO;
  58. }
  59. }
  60.  
  61. NSLog(@"\nDiscover New Devices!\n");
  62. NSLog(@"BLEInfo\n UUID:%@\n RSSI:%@\n\n",discoveredBLEInfo.discoveredPeripheral.identifier.UUIDString,discoveredBLEInfo.rssi);
  63.  
  64. [self.arrayBLE addObject:discoveredBLEInfo];
  65. [self.tableView reloadData];
  66. return YES;
  67. }
  68.  
  69. #pragma mark - Table view data source
  70.  
  71. - (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView {
  72. // Return the number of sections.
  73. return ;
  74. }
  75.  
  76. - (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
  77. // Return the number of rows in the section.
  78. return _arrayBLE.count;
  79. }
  80.  
  81. - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
  82. UITableViewCell *cell = [self.tableView dequeueReusableCellWithIdentifier:@"cell"];
  83.  
  84. // Step 2: If there are no cells to reuse, create a new one
  85. if(cell == nil) cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:@"cell"];
  86. // Add a detail view accessory
  87. BLEInfo *thisBLEInfo=[self.arrayBLE objectAtIndex:indexPath.row];
  88. cell.textLabel.text=[NSString stringWithFormat:@"%@ %@",thisBLEInfo.discoveredPeripheral.name,thisBLEInfo.rssi];
  89. cell.detailTextLabel.text=[NSString stringWithFormat:@"UUID:%@",thisBLEInfo.discoveredPeripheral.identifier.UUIDString];
  90. // Step 3: Set the cell text
  91.  
  92. // Step 4: Return the cell
  93. return cell;
  94. }
  95.  
  96. - (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath{
  97.  
  98. BLEInfo *thisBLEInfo=[self.arrayBLE objectAtIndex:indexPath.row];
  99. DetailViewController* dtvc=[self.storyboard instantiateViewControllerWithIdentifier:@"DetailViewController"];
  100. dtvc.centralMgr=self.centralMgr;
  101. dtvc.discoveredPeripheral=thisBLEInfo.discoveredPeripheral;
  102.  
  103. [self.navigationController pushViewController:dtvc animated:YES];
  104.  
  105. }
  106. @end

3.DetailViewController.h(连接具体的蓝牙,发现其内部信息)

  1. #import <UIKit/UIKit.h>
  2. #import <CoreBluetooth/CoreBluetooth.h>
  3.  
  4. @interface DetailViewController : UIViewController<
  5. CBPeripheralManagerDelegate,
  6. CBCentralManagerDelegate,
  7. CBPeripheralDelegate
  8. >
  9.  
  10. @property (nonatomic, strong) CBCentralManager *centralMgr;
  11. @property (nonatomic, strong) CBPeripheral *discoveredPeripheral;
  12. @property (strong, nonatomic) CBCharacteristic* writeCharacteristic;
  13.  
  14. @property int current_humitidy;
  15. @property int current_temperature;
  16.  
  17. - (IBAction)led1control:(id)sender;
  18.  
  19. @end

DetailViewController.m

  1. #import "DetailViewController.h"
  2.  
  3. @interface DetailViewController ()
  4.  
  5. @end
  6.  
  7. @implementation DetailViewController
  8.  
  9. #define SECTION_NAME @"Serviceinfo"
  10.  
  11. - (void)viewDidLoad
  12. {
  13. [super viewDidLoad];
  14.  
  15. [_centralMgr setDelegate:self];
  16. if (_discoveredPeripheral)
  17. {
  18. NSLog(@"connectPeripheral");
  19. [_centralMgr connectPeripheral:_discoveredPeripheral options:nil];
  20. }
  21. }
  22.  
  23. //界面退出
  24. -(void)viewWillDisappear:(BOOL)animated{
  25. [self.centralMgr cancelPeripheralConnection:_discoveredPeripheral];
  26. }
  27.  
  28. - (void)didReceiveMemoryWarning {
  29. [super didReceiveMemoryWarning];
  30. // Dispose of any resources that can be recreated.
  31. }
  32.  
  33. /*
  34. //========================================================================================
  35. //0.假设蓝牙关闭、掉线什么的,重新搜索
  36. - (void)centralManagerDidUpdateState:(CBCentralManager *)central
  37. {
  38. switch (central.state)
  39. {
  40. case CBCentralManagerStatePoweredOn:
  41. //[self.centralMgr scanForPeripheralsWithServices:nil options:nil];
  42. NSLog(@"start scan Peripherals");
  43.  
  44. break;
  45.  
  46. default:
  47. NSLog(@"Central Manager did change state");
  48. break;
  49. }
  50. }
  51.  
  52. //1.搜索后重连
  53. - (void)centralManager:(CBCentralManager *)central didDiscoverPeripheral:(CBPeripheral *)peripheral advertisementData:(NSDictionary *)advertisementData RSSI:(NSNumber *)RSSI
  54. {
  55. //[_centralMgr connectPeripheral:_discoveredPeripheral options:nil];
  56. }
  57. //========================================================================================
  58. */
  59.  
  60. //2.连接的Delegate 连接若成功则搜索服务
  61. - (void)centralManager:(CBCentralManager *)central didFailToConnectPeripheral:(CBPeripheral *)peripheral error:(NSError *)error
  62. {
  63. NSLog(@"didFailToConnectPeripheral : %@", error.localizedDescription);
  64. }
  65.  
  66. - (void)centralManager:(CBCentralManager *)central didConnectPeripheral:(CBPeripheral *)peripheral
  67. {
  68.  
  69. [_discoveredPeripheral setDelegate:self];
  70.  
  71. //查找服务
  72. [_discoveredPeripheral discoverServices:nil];
  73. }
  74.  
  75. //========================================================================================
  76. //3.搜索服务的Delegate 若发现服务,然后搜索其内的特征服务
  77.  
  78. - (void)peripheral:(CBPeripheral *)peripheral didDiscoverServices:(NSError *)error
  79. {
  80. if (error)
  81. {
  82. NSLog(@"didDiscoverServices : %@", [error localizedDescription]);
  83. // [self cleanup];
  84. return;
  85. }
  86.  
  87. for (CBService *s in peripheral.services)
  88. {
  89. NSLog(@"\n>>>服务UUID found with UUID : %@ des:%@", s.UUID,s.UUID.description);
  90. //查找特征字节
  91. [s.peripheral discoverCharacteristics:nil forService:s];
  92. }
  93. }
  94. //========================================================================================
  95. //4.搜索特征的Delegate 若发现特征,则看看这个“通道是发送的还是接收”,接收就read,发送就把这个writeCharacteristic记录下
  96. //注意:不是所有的特性值都是可读的(readable)。通过访问 CBCharacteristicPropertyRead 可以知道特性值是否可读。如果一个特性的值不可读,使用 peripheral:didUpdateValueForCharacteristic:error:就会返回一个错误。
  97. //Subscribing to a Characteristic’s Value(订制一个特性值) 尽管通过 readValueForCharacteristic:方法能够得到特性值,但是对于一个变化的特性值就不是很 有效了。大多数的特性值是变化的,比如一个心率监测应用,如果需要得到特性值,就需要 通过预定的方法获得。当预定了一个特性值,当值改变时,就会收到设备发出的通知。
  98.  
  99. /*特征值的属性:c.properties
  100. typedef NS_OPTIONS(NSInteger, CBCharacteristicProperties) {
  101. // 标识这个characteristic的属性是广播
  102. CBCharacteristicPropertyBroadcast= 0x01,
  103. // 标识这个characteristic的属性是读
  104. CBCharacteristicPropertyRead= 0x02,
  105. // 标识这个characteristic的属性是写-没有响应
  106. CBCharacteristicPropertyWriteWithoutResponse= 0x04,
  107. // 标识这个characteristic的属性是写
  108. CBCharacteristicPropertyWrite= 0x08,
  109. // 标识这个characteristic的属性是通知
  110. CBCharacteristicPropertyNotify= 0x10,
  111. // 标识这个characteristic的属性是声明
  112. CBCharacteristicPropertyIndicate= 0x20,
  113. // 标识这个characteristic的属性是通过验证的
  114. CBCharacteristicPropertyAuthenticatedSignedWrites= 0x40,
  115. // 标识这个characteristic的属性是拓展
  116. CBCharacteristicPropertyExtendedProperties= 0x80,
  117. // 标识这个characteristic的属性是需要加密的通知
  118. CBCharacteristicPropertyNotifyEncryptionRequiredNS_ENUM_AVAILABLE(NA, 6_0)= 0x100,
  119. // 标识这个characteristic的属性是需要加密的申明
  120. CBCharacteristicPropertyIndicateEncryptionRequiredNS_ENUM_AVAILABLE(NA, 6_0)= 0x200
  121. };
  122. */
  123. - (void)peripheral:(CBPeripheral *)peripheral didDiscoverCharacteristicsForService:(CBService *)service error:(NSError *)error
  124. {
  125. if (error)
  126. {
  127. NSLog(@"didDiscoverCharacteristicsForService error : %@", [error localizedDescription]);
  128. return;
  129. }
  130.  
  131. for (CBCharacteristic *c in service.characteristics)
  132. {
  133. NSLog(@"\n>>>\t特征UUID FOUND(in 服务UUID:%@): %@ (data:%@)",service.UUID.description,c.UUID,c.UUID.data);
  134.  
  135. /*
  136. 根据特征不同属性去读取或者写
  137. if (c.properties==CBCharacteristicPropertyRead) {
  138. }
  139. if (c.properties==CBCharacteristicPropertyWrite) {
  140. }
  141. if (c.properties==CBCharacteristicPropertyNotify) {
  142. }
  143. */
  144.  
  145. //假如你和硬件商量好了,某个UUID时写,某个读的,那就不用判断啦
  146. /*
  147. if([c.UUID isEqual:[CBUUID UUIDWithString:@"FFF1"]]){
  148. self.writeCharacteristic = c;
  149. }
  150. if([c.UUID isEqual:[CBUUID UUIDWithString:@"FFF6"]]){
  151. [peripheral readValueForCharacteristic:c];
  152. }*/
  153. if (c.properties==CBCharacteristicPropertyRead) {
  154. [peripheral readValueForCharacteristic:c];
  155. }
  156. }
  157. }
  158. //========================================================================================
  159.  
  160. - (void)peripheral:(CBPeripheral *)peripheral didUpdateValueForCharacteristic:(CBCharacteristic *)characteristic error:(NSError *)error
  161. {
  162. if (error)
  163. {
  164. NSLog(@"didUpdateValueForCharacteristic error : %@", error.localizedDescription);
  165. return;
  166. }
  167.  
  168. NSLog(@"\nFindtheValueis (UUID:%@):%@ ",characteristic.UUID,characteristic.value);
  169.  
  170. /*
  171. if([characteristic.UUID.description isEqualToString:@"FFF6"]){
  172. //我这里采用的是16进制数据,如<34001a00>,3400代表湿度十进制52.0,1a00代表温度26.0
  173. //当然你也可以有自己定义传输字符的意义
  174. NSData *datavalue=characteristic.value;
  175. NSData *shidudata=[datavalue subdataWithRange:NSMakeRange(0, 1)];
  176. NSData *wendudata=[datavalue subdataWithRange:NSMakeRange(2, 1)];
  177. NSLog(@"\nFind---theValueis:%@ %@-%@",characteristic.value,shidudata,wendudata);
  178. int i=0,j=0;
  179. [shidudata getBytes: &i length: sizeof(i)];
  180. [wendudata getBytes: &j length: sizeof(j)];
  181.  
  182. self.current_humitidy=i;
  183. self.current_temperature=j;
  184.  
  185. NSLog(@"\n室内温度为:%d℃,室内湿度为:%d%%",_current_temperature,_current_humitidy);
  186. }
  187. */
  188. }
  189.  
  190. - (void)peripheral:(CBPeripheral *)peripheral didUpdateNotificationStateForCharacteristic:(CBCharacteristic *)characteristic error:(NSError *)error {
  191. if (error) {
  192. NSLog(@"Error changing notification state: %@", [error localizedDescription]);
  193. }
  194. }
  195.  
  196. //向peripheral中写入数据后的回调函数
  197. - (void)peripheral:(CBPeripheral*)peripheral didWriteValueForCharacteristic:(CBCharacteristic *)characteristic error:(NSError *)error{
  198. NSLog(@"write value success : %@", characteristic);
  199. }
  200.  
  201. //自定义的写入数据的函数
  202. - (void)writeToPeripheral:(NSString *)string{
  203. if(!_writeCharacteristic){
  204. NSLog(@"writeCharacteristic is nil!");
  205. return;
  206. }
  207.  
  208. NSData* value = [self stringToByte:string];
  209. NSLog(@"Witedata: %@",value);
  210.  
  211. [_discoveredPeripheral writeValue:value forCharacteristic:_writeCharacteristic type:CBCharacteristicWriteWithResponse];
  212. }
  213.  
  214. //====================================================================================================
  215. //一些转换函数,本例中只用到stringToByte
  216. -(NSData*)stringToByte:(NSString*)string
  217. {
  218. NSString *hexString=[[string uppercaseString] stringByReplacingOccurrencesOfString:@" " withString:@""];
  219. if ([hexString length]%!=) {
  220. return nil;
  221. }
  222. Byte tempbyt[]={};
  223. NSMutableData* bytes=[NSMutableData data];
  224. for(int i=;i<[hexString length];i++)
  225. {
  226. unichar hex_char1 = [hexString characterAtIndex:i]; ////两位16进制数中的第一位(高位*16)
  227. int int_ch1;
  228. if(hex_char1 >= '' && hex_char1 <='')
  229. int_ch1 = (hex_char1-)*; //// 0 的Ascll - 48
  230. else if(hex_char1 >= 'A' && hex_char1 <='F')
  231. int_ch1 = (hex_char1-)*; //// A 的Ascll - 65
  232. else
  233. return nil;
  234. i++;
  235.  
  236. unichar hex_char2 = [hexString characterAtIndex:i]; ///两位16进制数中的第二位(低位)
  237. int int_ch2;
  238. if(hex_char2 >= '' && hex_char2 <='')
  239. int_ch2 = (hex_char2-); //// 0 的Ascll - 48
  240. else if(hex_char2 >= 'A' && hex_char2 <='F')
  241. int_ch2 = hex_char2-; //// A 的Ascll - 65
  242. else
  243. return nil;
  244.  
  245. tempbyt[] = int_ch1+int_ch2; ///将转化后的数放入Byte数组里
  246. [bytes appendBytes:tempbyt length:];
  247. }
  248. return bytes;
  249. }
  250.  
  251. //NSData类型转换成NSString
  252. - (NSString*)hexadecimalString:(NSData *)data{
  253. NSString* result;
  254. const unsigned char* dataBuffer = (const unsigned char*)[data bytes];
  255. if(!dataBuffer){
  256. return nil;
  257. }
  258. NSUInteger dataLength = [data length];
  259. NSMutableString* hexString = [NSMutableString stringWithCapacity:(dataLength * )];
  260. for(int i = ; i < dataLength; i++){
  261. [hexString appendString:[NSString stringWithFormat:@"%02lx", (unsigned long)dataBuffer[i]]];
  262. }
  263. result = [NSString stringWithString:hexString];
  264. return result;
  265. }
  266. //====================================================================================================
  267.  
  268. //假设有个swt1,开一下发送一个开关信号,控制LED灯
  269. - (IBAction)led1control:(id)sender {
  270. UISwitch *swt1= (UISwitch*)sender;
  271. if (swt1.on) {
  272. [self writeToPeripheral:@""];
  273. }else{
  274. [self writeToPeripheral:@""];
  275.  
  276. }
  277. }
  278.  
  279. @end

完整代码地址:https://github.com/rayshen/ShenBLETest

四、示例:基于蓝牙4.0的温湿度采集控制器

这是我自己做的湿度和温度的收集器和控制器。

iPhone收集来自单片机(蓝牙CC2541芯片)的温度和湿度信息,并且可以控制LED灯和继电器。

继电器就是一个开关,外围可以连接其他带电源和电器的大电路。

欢迎大家和我交流,我的微博是:weibo.com/rayshen1012

[iOS 基于CoreBluetooth的蓝牙4.0通讯]的更多相关文章

  1. CoreBluetooth——IOS蓝牙4.0使用心得

    原文链接:http://m.blog.csdn.net/article/details?plg_nld=1&id=51014318&plg_auth=1&plg_uin=1&a ...

  2. IOS学习之蓝牙4.0 BLE

    IOS学习也一段时间了,该上点干货了.前段时间研究了一下IOS蓝牙通讯相关的东西,把研究的一个成果给大家分享一下. 一 项目背景 简单介绍一下做的东西,设备是一个金融刷卡器,通过蓝牙与iphone手机 ...

  3. https://github.com/coolnameismy/BabyBluetooth github上的一个ios 蓝牙4.0的库并带文档和教程

    The easiest way to use Bluetooth (BLE )in ios,even bady can use. 简单易用的蓝牙库,基于CoreBluetooth的封装,并兼容ios和 ...

  4. IOS BLE蓝牙4.0

    前言: 自己做的项目里面有这么一个功能,总结归纳一下. 先导入必要的框架  CoreBluetooth.framework 在要用到蓝牙的文件里面导入以下头文件 #import <CoreBlu ...

  5. iOS蓝牙4.0

    iOS的蓝牙用到了  CoreBluetooth 框架 首先导入框架 #import <CoreBluetooth/CoreBluetooth.h> 我们需要一个管理者来管理蓝牙设备,CB ...

  6. iOS 蓝牙4.0开发

    背景: 1.iOS的蓝牙不能用来传输文件.2.iOS与iOS设备之间进行数据通信,使用gameKit.framework3.iOS与其他非iOS设备进行数据通信,使用coreBluetooth.fra ...

  7. iOS蓝牙4.0协议简单介绍

    iOS开发蓝牙4.0的框架是CoreBluetooth,本文主要介绍CoreBluetooth的使用,关于本文中的代码片段大多来自github上的一个demo,地址是myz1104/Bluetooth ...

  8. iOS蓝牙BLE4.0通信功能

    概述 iOS蓝牙BLE4.0通信功能,最近刚学的苹果,为了实现蓝牙门锁的项目,找了一天学习了下蓝牙的原理,亲手测试了一次蓝牙的通信功能,结果成功了,那么就把我学习的东西分享一下. 详细 代码下载:ht ...

  9. iOS蓝牙4.0开发

    文/starfox寒流(简书作者)原文链接:http://www.jianshu.com/p/974d165f78b5著作权归作者所有,转载请联系作者获得授权,并标注“简书作者”. iOS 蓝牙4.0 ...

随机推荐

  1. nginx图片处理相关

    nginx本身有支持图片处理的模块,通过外部插件也可以实现此功能. libgd的安装 前提是要有libgd的库文件, (1)去官网访问主页没问题,下载文件还是FQ下的,为了方便大家提供一个链接:htt ...

  2. eclipse/intellij idea 远程调试hadoop 2.6.0

    很多hadoop初学者估计都我一样,由于没有足够的机器资源,只能在虚拟机里弄一个linux安装hadoop的伪分布,然后在host机上win7里使用eclipse或Intellj idea来写代码测试 ...

  3. Caffe学习系列(23):如何将别人训练好的model用到自己的数据上

    caffe团队用imagenet图片进行训练,迭代30多万次,训练出来一个model.这个model将图片分为1000类,应该是目前为止最好的图片分类model了. 假设我现在有一些自己的图片想进行分 ...

  4. Java多线程之Runable与Thread

    Java多线程是Java开发中的基础内容,但是涉及到高并发就有很深的研究可做了. 最近看了下<Java并发实战>,发先有些地方,虽然可以理解,但是自己在应用中很难下手. 所以还是先回顾一下 ...

  5. 谈谈关于Python里面小数点精度控制的问题

    基础 浮点数是用机器上浮点数的本机双精度(64 bit)表示的.提供大约17位的精度和范围从-308到308的指数.和C语言里面的double类型相同.Python不支持32bit的单精度浮点数.如果 ...

  6. How to remove a batch of VMs and related Disks

    Foreword Need to remove a batch of VMs, which named with same prefix or belong to same Cloud Service ...

  7. EmitMapper的使用

    1.普通的映射. public class UserInfo { public int id { get; set; } public string name { get; set; } public ...

  8. 【BZOJ1003】【ZJOI2006】物流运输

    1003: [ZJOI2006]物流运输trans Time Limit: 10 Sec  Memory Limit: 162 MBSubmit: 2556  Solved: 1008[Submit] ...

  9. JavaScript的理解记录(4)

    客户端JavaScript:客户端就是Web浏览器; 一. 前奏: Web文档(document):一些呈现静态信息的页面,虽然有的页面是会动的,但信息本身还是静态! Web应用:可以动态载入信息,相 ...

  10. MVC认知路【点点滴滴支离破碎】【三】----IIS7.5上部署MVC4.0

    发布web到iis不能运行Google   ----- ╲ http://stackoverflow.com/questions/12057540/installing-asp-net-mvc-4-o ...