1.属性列表序列化

2.模型对象归档

3.嵌入式SQLite3

4.Core Data

5.应用程序设置

6.UIDocument管理文档存储

7.iCloud

Demo界面:

1.属性列表序列化

即从porperty list中直接读写plist对象(NSString, NSData, NSArray, or NSDictionary objects),其中容器对象中的实例亦要为plist对象。

根视图控制器:

 #define kFilename @"data.plist"

 - (void)viewDidLoad
{
[super viewDidLoad];
NSString *path=[self dataFilePath]; //获取document下的指定文件路径
NSLog(@"%@",path);
if([[NSFileManager defaultManager] fileExistsAtPath:path])
{
NSArray *array=[[NSArray alloc] initWithContentsOfFile:path];
self.field1.text=[array objectAtIndex:];
self.field2.text=[array objectAtIndex:];
self.field3.text=[array objectAtIndex:];
self.field4.text=[array objectAtIndex:];
} UIApplication *app =[UIApplication sharedApplication];
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(applicationWillResignActive:) name:UIApplicationWillResignActiveNotification object:app];
} -(NSString *)dataFilePath
{
NSArray *paths=NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory=[paths objectAtIndex:];
return [documentsDirectory stringByAppendingPathComponent:kFilename];
} -(void)applicationWillResignActive:(NSNotification *)notification;
{
NSMutableArray *array=[[NSMutableArray alloc] init];
[array addObject:field1.text];
[array addObject:field2.text];
[array addObject:field3.text];
[array addObject:field4.text];
[array writeToFile:[self dataFilePath] atomically:YES]; //没有则自动创建文件,和c中的fopen("","w")一样,先清空内容再写入。
//所以没有判断是否文件存在。
}

沙盒中的Documents文件夹有生成data.plist,且用xml协议保存了数据。

 
 

2.模型对象归档

NSString、NSArray、NSData、NSDictionary都实现了NSCoding协议,可直接通过调用writeToFile归档。

但如果想保持对象类型的数据,则需要到该方法灵活实现。首先可将需归档的对象先实现NSCoding协议,重写encodeWithCode方法和initWithCode方法,然后通过NSKeyedArchiver转换为NSData,然后通过NSData的writeToFile方法写入到文件,或者将转换后的NSData放入到NSArray或NSDictionary中调用writeToFile写入到文件便可实现包装了自定义类型的数据和字典的归档;

通过NSKeyedUnarchiver读取归档文件到对象,或者通过NSArray的arrrayWithContentsOfFile或NSDictionary的dictionaryWithContentsOfFile到数组对象或字典,然后取出序列化过的自定义对象(即自定义对象的NSData形式),然后通过NSKeyedUnarchiver反归档到对象。

根视图控制器:
#define kFilename @"archive"
#define kDataKey @"Data"
-(NSString *)dataFilePath
{
NSArray *paths=NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory=[paths objectAtIndex:]; return [documentsDirectory stringByAppendingPathComponent:kFilename];
} - (void)viewDidLoad
{
[super viewDidLoad];
if ([[NSFileManager defaultManager] fileExistsAtPath:[self dataFilePath]])
{
NSMutableData *data=[[NSMutableData alloc] initWithContentsOfFile:[self dataFilePath]];
NSKeyedUnarchiver *unarchiver=[[NSKeyedUnarchiver alloc] initForReadingWithData:data];
BIDFourLines *fourlines=[unarchiver decodeObjectForKey:kDataKey];
[unarchiver finishDecoding];
field1.text=fourlines.field1;
field2.text=fourlines.field2;
field3.text=fourlines.field3;
field4.text=fourlines.field4;
} UIApplication *app =[UIApplication sharedApplication];
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(applicationWillResignActive:) name:UIApplicationWillResignActiveNotification object:app];
} -(void)applicationWillResignActive:(NSNotification *)notification;
{
BIDFourLines *fourlines=[[BIDFourLines alloc] init];
fourlines.field1=field1.text;
fourlines.field2=field2.text;
fourlines.field3=field3.text;
fourlines.field4=field4.text;
NSMutableData *data=[[NSMutableData alloc] init];
NSKeyedArchiver *archiver=[[NSKeyedArchiver alloc] initForWritingWithMutableData:data];//将archiver在收到编码后数据自动转为二进制写到data
[archiver encodeObject:fourlines forKey:kDataKey];//以Data为键编码
[archiver finishEncoding];
[data writeToFile:[self dataFilePath] atomically:YES]; //将data写入Documents中的archiver中。 }

/*

writeToFile:

这方法其实是写到plist文件(生成plist文件中的一个档)中的,根据官方文档描述If the array’s contents are all property list objects (NSString, NSData, NSArray, or NSDictionary objects), the file written by this method can be used to initialize a new array with the class method arrayWithContentsOfFile: or the instance method initWithContentsOfFile:. This method recursively validates that all the contained objects are property list objects before writing out the file, and returns NO if all the objects are not property list objects, since the resultant file would not be a valid property list.

*/

模型对象:
 #pragma mark NSCoding
-(void)encodeWithCoder:(NSCoder *)aCoder
{
[aCoder encodeObject:field1 forKey:kField1Key];
[aCoder encodeObject:field2 forKey:kField2Key];
[aCoder encodeObject:field3 forKey:kField3Key];
[aCoder encodeObject:field4 forKey:kField4Key];
} -(id)initWithCoder:(NSCoder *)aDecoder
{
if(self=[super init])
{
self.field1=[aDecoder decodeObjectForKey:kField1Key];
self.field2=[aDecoder decodeObjectForKey:kField2Key];
self.field3=[aDecoder decodeObjectForKey:kField3Key];
self.field4=[aDecoder decodeObjectForKey:kField4Key];
}
return self;
} #pragma mark NSCopying
-(id)copyWithZone:(NSZone *)zone
{
BIDFourLines *copy=[[[self class] allocWithZone:zone] init];
copy.field1=[self.field1 copyWithZone:zone];
copy.field2=[self.field2 copyWithZone:zone];
copy.field3=[self.field3 copyWithZone:zone];
copy.field4=[self.field4 copyWithZone:zone]; return copy;
}

沙盒中的Documents文件夹生成archiver文件(无扩展名,加上.plist扩展名即可查看编码后保存的数据内容)。

 
 

3.嵌入式SQLite3

需要先导入sqlite3 的 api 或 framework。
 
 #define kFilename @"data.sqlite3"

 - (void)viewDidLoad
{
[super viewDidLoad];
sqlite3 *database;
if(sqlite3_open([[self dataFilePath] UTF8String], &database)!=SQLITE_OK)
{
sqlite3_close(database);
NSAssert(, @"Failed to open database");
} NSString *createSQL=@"CREATE TABLE IF NOT EXISTS FIELDS"
"(ROW INTEGER PRIMARY KEY , FIELD_DATA TEXT);";
char *errorMsg;
if(sqlite3_exec(database, [createSQL UTF8String], NULL, NULL, &errorMsg)!=SQLITE_OK)
{
sqlite3_close(database);
NSAssert(, @"Error creating table: %s",errorMsg);
}
NSString *query=@"SELECT ROW, FIELD_DATA FROM FIELDS ORDER BY ROW";
sqlite3_stmt *statement;
if(sqlite3_prepare_v2(database, [query UTF8String], -, &statement, nil)==SQLITE_OK)
{
while (sqlite3_step(statement)==SQLITE_ROW) //移动位置指针
{
int row=sqlite3_column_int(statement,);
char *rowData=(char *)sqlite3_column_text(statement, ); NSString *fieldName=[[NSString alloc] initWithFormat:@"field%d",row];
NSString *fieldValue=[[NSString alloc] initWithUTF8String:rowData];
UITextField *field=[self valueForKey:fieldName];
field.text=fieldValue;
}
sqlite3_finalize(statement);
}
sqlite3_close(database); UIApplication *app =[UIApplication sharedApplication];
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(applicationWillResignActive:) name:UIApplicationWillResignActiveNotification object:app];
} -(void)applicationWillResignActive:(NSNotification *)notification;
{
sqlite3 *database;
if(sqlite3_open([[self dataFilePath] UTF8String], &database)!=SQLITE_OK)
{
sqlite3_close(database);
NSAssert(, @"Failed to open database");
} for (int i=; i<=; i++) {
NSString *fieldName=[[NSString alloc] initWithFormat:@"field%d",i];
UITextField *field=[self valueForKey:fieldName]; char *updata="INSERT OR REPLACE INTO FIELDS (ROW, FIELD_DATA) VALUES(? , ?);";
sqlite3_stmt *stmt;
if (sqlite3_prepare_v2(database, updata, -, &stmt, nil)==SQLITE_OK) {
sqlite3_bind_int(stmt, , i);
sqlite3_bind_text(stmt, , [field.text UTF8String],-,NULL);
}
if(sqlite3_step(stmt)!=SQLITE_DONE)
{
NSAssert(,@"Error updating table.");
}
sqlite3_finalize(stmt);
}
sqlite3_close(database);
}

沙盒中的Documents文件夹生成data.sqlite3文件(未知直读方法)。

 
 

4.Core Data

创建项目时选空模板才有use core data (ORM对象关系映射)选项 选择。之后再配置xcdatamodel和根视图。
xcdatamodel配置:

根视图控制器:
 - (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view from its nib. BIDAppDelegate *appDelegate=[[UIApplication sharedApplication] delegate];
NSManagedObjectContext *context=[appDelegate managedObjectContext];
NSEntityDescription *entityDecription=[NSEntityDescription entityForName:@"Line" inManagedObjectContext:context];//关联实体与上下文
NSFetchRequest *request=[[NSFetchRequest alloc] init];
[request setEntity:entityDecription];//设置抓取实体
NSError *error;
/*因为要抓取实体中的所有项,所以没有设置抓取属性*/
NSArray *objects=[context executeFetchRequest:request error:&error];//从实体中抓取到上下文,且上下文进行跟踪对象
if(objects==nil)
NSLog(@"There was an error!");
for (NSManagedObject *object in objects)
{
NSNumber *lineNum=[object valueForKey:@"lineNum"]; //读取抓取出的第n个对象的lineNum属性
NSString *lineText=[object valueForKey:@"lineText"]; NSString *fieldname=[[NSString alloc] initWithFormat: @"line%d",[lineNum integerValue]];
UITextField *field=[self valueForKey:fieldname];
field.text=lineText;
} UIApplication *app=[UIApplication sharedApplication];
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(applicationWillResignActive:) name:UIApplicationWillResignActiveNotification object:app];
} -(void)applicationWillResignActive:(NSNotification *)notification
{
BIDAppDelegate *appDelegate=[[UIApplication sharedApplication] delegate];
NSManagedObjectContext *context=[appDelegate managedObjectContext];
NSError *error; for (int i=; i<=; i++) {
NSString *fieldname=[[NSString alloc] initWithFormat:@"line%d",i];
UITextField *field=[self valueForKey:fieldname]; NSFetchRequest *request=[[NSFetchRequest alloc] init]; NSEntityDescription *entityDescritption=[NSEntityDescription entityForName:@"Line" inManagedObjectContext:context];
[request setEntity:entityDescritption]; NSPredicate *predicate=[NSPredicate predicateWithFormat:@"(lineNum=%d)",i];
[request setPredicate:predicate]; NSArray *objects=[context executeFetchRequest:request error:&error];//抓取上下文中的托管对象集
NSManagedObject *theLine=nil; if(objects==nil)
NSLog(@"There was an error!");
if([objects count]>)
{
/*因设置了抓取属性,每次按抓取属性在实体抓取的上下文中的托管对象集里都只有一个对应的托管对象(在此例对应抓取属性的只有一个)*/
theLine=[objects objectAtIndex:];//取托管对象
}
else
{
/*在实体中插入新的托管对象,且返回该对象和放入上下文中跟踪*/
theLine=[NSEntityDescription insertNewObjectForEntityForName:@"Line" inManagedObjectContext:context];
}
[theLine setValue:[NSNumber numberWithInt:i] forKey:@"lineNum"];
[theLine setValue:field.text forKey:@"lineText"];
}
[context save:&error];//跟踪结束,保存进实体
}

应用程序委托:

 - (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
// Override point for customization after application launch.
self.rootcontroller=[[BIDViewController alloc] initWithNibName:@"BIDViewController" bundle:nil];
UIView *rootView=self.rootcontroller.view;
CGRect viewFrame=rootView.frame;
viewFrame.origin.y+=[UIApplication sharedApplication].statusBarFrame.size.height;
rootView.frame=viewFrame;
[self.window addSubview:rootView];
self.window.backgroundColor = [UIColor whiteColor];
[self.window makeKeyAndVisible];
return YES;
}

沙盒中的Documents文件夹生成Core_Data_Persistence.sqlite文件(未知直读方法)。

 
 

其它例子

5.应用程序设置(UserDefault)

程序使用该方法保持的数据,可在iphone的settings中查看和设置。

添加setting.bundle,在root.plist中配置好要保存的数据项和settings中显示的分组界面。

应用程序委托:
 - (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
// Override point for customization after application launch.
NSDictionary *defaults=[NSDictionary dictionaryWithObjectsAndKeys:[NSNumber numberWithBool:YES],kWarpDriveKey,[NSNumber numberWithInt:],kWarpFactorKey,@"Greed",kFavoriteSinKey, nil];
[[NSUserDefaults standardUserDefaults] registerDefaults:defaults];
return YES;
}//第一次运行程序时,对设置束赋默认初值。

视图控制器:

     NSUserDefaults *defaults=[NSUserDefaults standardUserDefaults];
usernameLabel.text=[defaults objectForKey:kUsernameKey];
//读取方法,利用NSUserDefaults的单例方法。键值为设置束中的每项的Identifier。 NSUserDefaults *defaults=[NSUserDefaults standardUserDefaults];
[defaults setBool:engineSwitch.on forKey:kWarpDriveKey];
//保存方法
在Settings中可设置应用程序,在应用程序中亦可设置反馈给Settings。Documents文件夹中没有生成数据保存文件。
 
 

6.UIDocument管理文档存储

模型类:
先建立作为UIDocument子类的数据模型类,在类里实现以下UIDocument方法和其它模型方法
 -(id)contentsForType:(NSString *)typeName error:(NSError *__autoreleasing *)outError
{
NSLog(@"saving document to URL %@",self.fileURL);//输出保存的路径
return [bitmap copy];//bitmap为保存的mutabledata数据
}//保存 -(BOOL)loadFromContents:(id)contents ofType:(NSString *)typeName error:(NSError *__autoreleasing *)outError
{
NSLog(@"loading document from URL %@",self.fileURL);
self.bitmap =[contents copy];
return true;
}//加载

控制器:

读取文档路径集
 NSArray *paths=NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *path=[paths objectAtIndex:];
NSFileManager *fm=[NSFileManager defaultManager];
NSError *dirError;
NSArray *files=[fm contentsOfDirectoryAtPath:path error:&dirError];
//数组内排序
self.documentFileNames=files;

读取文档URL路径

 -(NSURL *)urlForFilename:(NSString *)filename
{
NSArray *paths=NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentDirectory=[paths objectAtIndex:];
NSString *filePath=[documentDirectory stringByAppendingPathComponent:filename];
NSURL *url=[NSURL fileURLWithPath:filePath];
return url;

创建文档,并设置保存

         NSString *filename=[NSString stringWithFormat:@"%@.tinypix",[alertView textFieldAtIndex:].text];
NSURL *saveUrl=[self urlForFilename:filename];
self.chooseDocument=[[BIDTinyPixDocument alloc] initWithFileURL:saveUrl];//创建UIDocument子类实例对象
[chooseDocument saveToURL:saveUrl forSaveOperation:UIDocumentSaveForCreating completionHandler:^(BOOL success) {
if(success)
{
NSLog(@"save OK");
//addition
}
else
NSLog(@"failed to save!");
}];

打开文档

         self.chooseDocument=[[BIDTinyPixDocument alloc] initWithFileURL:docUrl];
[self.chooseDocument openWithCompletionHandler:^(BOOL success) {
if(success)
{
NSLog(@"load OK");
//addition
}
else
NSLog(@"failed to load!");
}];

关闭文档(保持编辑数据)

 UIDocument *doc=self.chooseDocument;
[doc closeWithCompletionHandler:nil];

沙盒中的Documents文件夹生成filename.tinypix文件。

 
 

7.iCloud

首先设置好provisioning profile和Entitlements部分,获取icloud的权限。
控制器:
查询icloud中指定扩展名的文档路径集,得到路径后保存方法和文档保存方法一致。
 -(void)reloadFiles
{
NSFileManager *fileManager=[NSFileManager defaultManager];
NSURL *cloudURL=[fileManager URLForUbiquityContainerIdentifier:nil];
NSLog(@"got cloudURL %@",cloudURL); self.query=[[NSMetadataQuery alloc] init]; query.predicate=[NSPredicate predicateWithFormat:@"%K like '*.tinypix'",NSMetadataItemFSNameKey];
query.searchScopes=[NSArray arrayWithObject:NSMetadataQueryUbiquitousDocumentsScope]; [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(updateUbiquitousDocuments:) name:NSMetadataQueryDidFinishGatheringNotification object:nil];
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(updateUbiquitousDocuments:) name:NSMetadataQueryDidUpdateNotification object:nil]; [query startQuery];
} -(void)updateUbiquitousDocuments:(NSNotification *)notification
{
self.documentURLs=[NSMutableArray array];
self.documentFileNames=[NSMutableArray array];
NSLog(@"updateUbiquitousDocuments, results= %@",self.query.results); NSArray *results=[self.query.results sortedArrayUsingComparator:^NSComparisonResult(id obj1, id obj2) {
NSMetadataItem *item1=obj1;
NSMetadataItem *item2=obj2;
return [[item2 valueForAttribute:NSMetadataItemFSCreationDateKey] compare:[item1 valueForAttribute:NSMetadataItemFSCreationDateKey]];
}]; for(NSMetadataItem *item in results)
{
NSURL *url=[item valueForAttribute:NSMetadataItemURLKey];
[self.documentURLs addObject:url];
[(NSMutableArray *)documentFileNames addObject:[url lastPathComponent]];
}
[self.tableView reloadData];
} -(NSURL *)urlForFilename:(NSString *)filename
{
NSURL *baseURL=[[NSFileManager defaultManager] URLForUbiquityContainerIdentifier:nil];
NSURL *pathURL=[baseURL URLByAppendingPathComponent:@"Documents"];
NSURL *destinationURL=[pathURL URLByAppendingPathComponent:filename];
return destinationURL;
}

icloud上读写首选项

     NSUbiquitousKeyValueStore *prefs=[NSUbiquitousKeyValueStore defaultStore];
[prefs setLongLong:selectedColorIndex forKey:@"selectedColorIndex"];
self.selectedColorIndex=[prefs longLongForKey:@"selectedColorIndex"];

(IOS)数据持久化的更多相关文章

  1. iOS 数据持久化(扩展知识:模糊背景效果和密码保护功能)

    本篇随笔除了介绍 iOS 数据持久化知识之外,还贯穿了以下内容: (1)自定义 TableView,结合 block 从 ViewController 中分离出 View,轻 ViewControll ...

  2. iOS开发笔记-swift实现iOS数据持久化之归档NSKeyedArchiver

    IOS数据持久化的方式分为三种: 属性列表 (plist.NSUserDefaults) 归档 (NSKeyedArchiver) 数据库 (SQLite.Core Data.第三方类库等 归档(又名 ...

  3. IOS数据持久化之归档NSKeyedArchiver

    IOS数据持久化的方式分为三种: 属性列表 (自定义的Property List .NSUserDefaults) 归档 (NSKeyedArchiver) 数据库 (SQLite.Core Data ...

  4. iOS -数据持久化方式-以真实项目讲解

    前面已经讲解了SQLite,FMDB以及CoreData的基本操作和代码讲解(CoreData也在不断学习中,上篇博客也会不断更新中).本篇我们将讲述在实际开发中,所使用的iOS数据持久化的方式以及怎 ...

  5. iOS数据持久化方式及class_copyIvarList与class_copyPropertyList的区别

    iOS数据持久化方式:plist文件(属性列表)preference(偏好设置)NSKeyedArchiver(归档)SQLite3CoreData沙盒:iOS程序默认情况下只能访问自己的程序目录,这 ...

  6. iOS数据持久化-OC

    沙盒详解 1.IOS沙盒机制 IOS应用程序只能在为该改程序创建的文件系统中读取文件,不可以去其它地方访问,此区域被成为沙盒,所以所有的非代码文件都要保存在此,例如图像,图标,声音,映像,属性列表,文 ...

  7. iOS数据持久化

    在iOS中,实现数据持久化一般分为4大种: 1.属性列表 2.对象归档 3.SQLite 4.Core Data 一.属性列表 NSUserDefaults类的使用和NSKeyedArchiver有很 ...

  8. iOS数据持久化存储:归档

    在平时的iOS开发中,我们经常用到的数据持久化存储方式大概主要有:NSUserDefaults(plist),文件,数据库,归档..前三种比较经常用到,第四种归档我个人感觉用的还是比较少的,恰恰因为用 ...

  9. 转载 -- iOS数据持久化存储

    作者:@翁呀伟呀 授权本站转载 概论 所谓的持久化,就是将数据保存到硬盘中,使得在应用程序或机器重启后可以继续访问之前保存的数据.在iOS开发中,有很多数据持久化的方案,接下来我将尝试着介绍一下5种方 ...

  10. iOS 数据持久化(1):属性列表与对象归档

    @import url(http://i.cnblogs.com/Load.ashx?type=style&file=SyntaxHighlighter.css); @import url(/ ...

随机推荐

  1. IOS学习之蓝牙4.0

    1建立中心角色 1 2 3 #import <CoreBluetooth/CoreBluetooth.h>  CBCentralManager *manager;  manager = [ ...

  2. UIView 中bounds和frame的差别

    搞iOS开发的童鞋基本都会用过UIView,那他的bounds和frame两个属性也不会陌生,那这两个有什么实质性的区别呢? 先看到下面的代码你肯定就明白了一些: -(CGRect)frame{    ...

  3. 180行ruby代码搞定游戏2048

    最今在玩2048这款小游戏,游戏逻辑简单,很适合我这样的对于游戏新入行的人来实现逻辑.于是选择了最拿手的ruby语言来实现这款小游戏的主要逻辑.还是挺简单的,加起来4小时左右搞定. 上代码: requ ...

  4. [C# 基础知识系列]专题六:泛型基础篇——为什么引入泛型

    引言: 前面专题主要介绍了C#1中的2个核心特性——委托和事件,然而在C# 2.0中又引入一个很重要的特性,它就是泛型,大家在平常的操作中肯定会经常碰到并使用它,如果你对于它的一些相关特性还不是很了解 ...

  5. js执行环境相关

    Js执行过程 如果一个文档中存在多个代码段 步骤一:读入第一个代码段(js引擎并非一行一行执行,而是一段一段分析执行) 步骤二:做词法分析和语法分析,有错则报语法错误(比如括号不匹配等),并跳转到步骤 ...

  6. 安卓中onBackPressed ()方法的使用

    一.onBackPressed()方法的解释 这个方法放在 void android.app.Activity.onBackPressed() 在安卓API中它是这样解释的: public void ...

  7. Oracle Enterprise Manager 11g 输入用户名和口令 点击“登录”按键后没反应,也不报错,是什么原因?

    在tnsnames.ora文件中检查设置好像没什么问题,用sqlplus也可以正常操作orcl 问题找到了,其实可简单,https://localhost:1158/em/console/logon/ ...

  8. UVA 10798 - Be wary of Roses (bfs+hash)

    10798 - Be wary of Roses You've always been proud of your prize rose garden. However, some jealous f ...

  9. C#代码模拟http发送get和post请求

    private string HttpPost(string Url, string postDataStr) { HttpWebRequest request = (HttpWebRequest)W ...

  10. 发生了Post错误:错误代码40005,微信返回错误信息:invalid file type

    给客户部署 PxxCms, 使用群发功能发送图文的的时候提示: 发生了Post错误:错误代码40005,微信返回错误信息:invalid file type, 没学过php伤不起 ... Google ...