ios開發中的4種數據持久化方式【二、資料庫 SQLite3、Core Data 的運用】

来源:http://www.cnblogs.com/azuo/archive/2016/01/27/5145632.html
-Advertisement-
Play Games

在上文,我們介紹了ios開發中的其中2種數據持久化方式:屬性列表、歸檔解檔。本節將繼續介紹另外2種iOS持久化數據的方法:資料庫 SQLite3、Core Data 的運用; 在本節,將通過對4個文本框內容的創建、修改,退出後臺,再重新回到後臺,來認識這兩種持久化數據的方式。效果圖如下【圖1】: 【


               在上文,我們介紹了ios開發中的其中2種數據持久化方式:屬性列表、歸檔解檔本節將繼續介紹另外2種iOS持久化數據的方法:資料庫 SQLite3、Core Data 的運用

在本節,將通過對4個文本框內容的創建、修改,退出後臺,再重新回到後臺,來認識這兩種持久化數據的方式。效果圖如下【圖1】:

 

【圖1 GUI界面效果圖】

【本次開發環境: Xcode:7.2     iOS Simulator:iphone6S plus   By:啊左】    

 

 

一、資料庫SQLite3

SQLite(Strutcured Query Language,結構化查詢語言),是iOS的嵌入式SQL資料庫,在存儲和檢索大量數據方面非常有效,屬於輕量級資料庫,但是功能很強大。 安卓和ios開發使用的都是SQLite資料庫。    而另一種持久化數據方式,core Data是對SQLite的封裝,因為iOS中使用的SQLite是純C語言的。

 

1、鏈接到SQLite3庫

在Xcode中,使用Single View Application模板創建一個新項目,命名為persistence3。

新建項目選中項目導航列表(最左邊)的頂部然後在主區域的TARGETS部分選中persistence3,註意要從TARGETS選中而不是從PROJECT部分。

選中後,點擊“Build Phases”,打開在第三欄,按“+”添加“libsqlite3.0.tbd”【註意:Xcode7後dylib尾碼改成tbd,如果仍要添加.bylib為尾碼的鏈接,在添加framework那個對話框,最下麵有個 "add other..." 點開之後, 按command+shift+G , 路徑輸入 /usr/lib/  ,然後 找到你需要的lib文件 ok了。。 好吧,我還是習慣添加.dyib...

【圖2 鏈接SQLite3.dyib】

3是版本號,是SQLite的第三個版本。它是始終指向最新版本的SQLite3庫的;   在“Main.storyboard”中拖入4個標簽、4個文本框控制項,拖動並對齊標簽與文本框,並依次修改標簽文本如【圖1】,“ViewController.h”中添加一個裝載4個文本框的數組“lineFields
#import <UIKit/UIKit.h>
@interface ViewController : UIViewController

@property (nonatomic,strong)IBOutletCollection(UITextField) NSArray *lineFields;//存儲4個文本框欄位的數組
@end

然後打開輔助編輯器,通過control鍵將4個文本框連接到 lineFields 這個數組,確保連接順序為從頂部到底部!

 

在項目導航面板中,點擊"ViewController.m" ,將以下2段代碼添加到 @implementation與 @end 的中間,與上文相同,這個方法在後面會一直調用:

#import "ViewController.h"
#import <sqlite3.h>         //導入SQLite3,註意是擴折號

//SQLite 是不區分大小寫的

@implementation ViewController
{
    sqlite3 *sqlite; //資料庫
}

//懶載入
-(NSString *)datafilePath
{
    NSArray *array = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
    NSString *path = [array objectAtIndex:0];
    return [path stringByAppendingPathComponent:@"data.sqlite"];
}

在這裡,我們介紹一下iOS9的一個新的變化:UIAlertController。小小地在這裡運用一下:

//警告提示框,為後面的操作向用戶提示信息
-(void)alert:(NSString *)mes
{
    /*知識點:ios 9.0 後,簡單的UIAlertView已經不能用了。
     UIAlertController代替了UIAlertView彈框 和 UIActionSheet下彈框
     */
    //UIAlertControllerStyleAlert:中間;  UIAlertControllerStyleActionSheet:顯示在屏幕底部;
    UIAlertController *alert = [UIAlertController alertControllerWithTitle:@"警告" message:mes preferredStyle:(UIAlertControllerStyleAlert)];
    UIAlertAction *cancel = [UIAlertAction actionWithTitle:@"取消" style:(UIAlertActionStyleCancel) handler:nil];
    UIAlertAction *defult = [UIAlertAction actionWithTitle:@"確定" style:(UIAlertActionStyleDefault) handler:nil];
    [alert addAction:cancel];
    [alert addAction:defult];
    [self presentViewController:alert animated:YES completion:nil]; //呈現
}

 

- (void)viewDidLoad 以及通知的方法代碼:

 1 - (void)viewDidLoad {
 2     [super viewDidLoad];
 3     int result = sqlite3_open([[self datafilePath]UTF8String], &sqlite);
 4     //不等於SQLITE_OK,則表示打開資料庫的時候遇到問題
 5     if(result != SQLITE_OK)
 6     {
 7         sqlite3_close(sqlite);
 8         [self alert:@"資料庫打開失敗"];
 9     }
10     
11     //定義一個語句,其中if not exists表示:如果不存在數據表,則新建一個。 若存在,則此命令自動退出. 所以這個語句可以在每次啟動時調用
12     NSString *createSql = @"CREATE TABLE IF NOT EXISTS 'wenbenkuang'(id INTEGER PRIMARY KEY,datatext TEXT NOT NULL)";
13     char * error;
14     int ret = sqlite3_exec(sqlite,[createSql UTF8String], NULL, NULL, &error); //SQLite是純C語言的。SQL語句需要使用“UTF8String”方法把NSString轉換為char.
15     if(ret != SQLITE_OK)
16     {
17         [self alert:[NSString stringWithFormat:@"數據表創建失敗%s",error]];
18     }
19     
20     //使用select語句載入數據,並要求資料庫按行號準備排序,以便我們以相同的順序獲取,否則將使用sqlite3內部存儲順序
21     NSString *preSql = @"SELECT id,datatext FROM 'wenbenkuang'ORDER BY id";
22     sqlite3_stmt *statmt;
23     if(sqlite3_prepare_v2(sqlite,[preSql UTF8String], -1, &statmt, nil) == SQLITE_OK) //SQLITE_OK表成功載入
24     {
25         while (sqlite3_step(statmt) == SQLITE_ROW) 
26         {
27             int row = sqlite3_column_int(statmt, 0);                //獲取行號
28             char *rowData = (char *)sqlite3_column_text(statmt, 1); //獲取該行數據
29             NSString *dataString = [[NSString alloc]initWithUTF8String:rowData];
30             UITextField *textfield = self.lineFields[row];
31             textfield.text = dataString;
32         }
33         //完成陳述
34         sqlite3_finalize(statmt);
35     }
36     //關閉資料庫
37     sqlite3_close(sqlite);
38     
39     //註冊一個觀測者,進入後臺時發送通知;
40     UIApplication *app = [UIApplication sharedApplication];
41     [[NSNotificationCenter defaultCenter]addObserver:self selector:@selector(applicationWillResignActiveNotification:) 
name:UIApplicationWillResignActiveNotification object:app]; 42 } 43 -(void)applicationWillResignActiveNotification:(NSNotification *)notification 44 { 45 int result = sqlite3_open([[self datafilePath] UTF8String], &sqlite); 46 if (result != SQLITE_OK) { 47 [self alert:@"資料庫打開失敗"]; 48 sqlite3_close(sqlite); 49 } 50 for(int i=0;i<4;i++) 51 { 52 UITextField *tetxField = self.lineFields[i]; 53 char *updataSql = "INSERT OR REPLACE INTO 'wenbenkuang'(id,datatext) VALUES(?,?);"; 54 sqlite3_stmt *stmt; 55 if(sqlite3_prepare_v2(sqlite, updataSql, -1, &stmt, nil) == SQLITE_OK) 56 { 57 sqlite3_bind_int(stmt, 1, i); 58 sqlite3_bind_text(stmt, 2, [tetxField.text UTF8String], -1, NULL); 59 } 60 if(sqlite3_step(stmt) != SQLITE_DONE) 61 { 62 [self alert:@"數據更新失敗"]; 63 } 64 sqlite3_finalize(stmt); 65 } 66 sqlite3_close(sqlite); 67 }

在這段的viewDidLoad代碼中:

(行號為3-9)我們首先創建或者打開資料庫,如果打開時遇到問題,則拋出警告框。

(行號為11-18)資料庫將所有的數據存儲在表中。因此,創建一個名為“wenbenkuang”數據表,包含一個標識為“id”的鍵,與一個名為"datatext"的不為空的文本項,如果已存在相同名稱的表,則退出創建,不執行操作,所以該資料庫語句可以在每次啟動時調用一次,而不會影響到現有的資料庫;【SQLite是純C語言的。SQL語句需要使用“UTF8String”方法把NSString轉換為char.】

(行號為20-23)載入數據,使select語句載入數據,並要求資料庫按行號準備排序,以便我們以相同的順序獲取,否則將使用sqlite3內部存儲順序;   (行號為25-32)遍歷返回各行,定義一個int和char獲取數據,然後,我們通過從資料庫獲取的數據設置我們的文本欄位。   最後,關閉資料庫,操作結束;   在 “applicationWillResignActiveNotification:” 方法中,我們也是首先打開資料庫,創建一個欄位名稱,以便檢測到輸出,然後設計一條帶2個綁定變數的INSERT OR REPLACE的SQL語句,第一變數表行,第二個表存儲的實際欄位值,接下來聲明一個指向語句的指針,為語句添加綁定變數,並將值綁定到2個綁定標量中, 通過調用sqlite3_step來執行更新,迴圈執行該語句。 完成後,關閉操作資料庫;接下來我們運行調試一下。   按“command+R”運行程式,為4個文本框輸入欄位,關閉Xcode,或按下“command+shift”,點擊2次“H”鍵,退出該應用,然後再次打開, 看看是是否文本框中保留有原來自己的輸入的欄位。   二、Core Data的運用   同樣的,這次我們依然通過創建一個簡單的persistence應用,來展示如何通過蘋果自帶的Core Data框架來實現持久化。  第一步,我們應該很熟悉了。在Xcode中,使用Single View Application模板創建一個新項目,命名為persistence4。 如【圖3】,先別按Next,勾選“Use Core Data”,其中“Devices”為設備選項,你可以選擇“iphone”或者“ipad”,這裡我們選擇通用“Universal”。點擊Next! 【圖3 創建persistence4】 這次在敲入代碼前,我們還需要進行一系列的討論,好吧。。。“Core Data”確實麻煩些。  1、Core Data的數據模型 之前,如上文的iOS開發中的4種數據持久化方式【一、屬性列表與歸檔解檔】所介紹的,在使用Core Data之前我們創建數據模型的方式便是創建一個NSObject的子類並讓它們遵循NSCoding和NSCopying協議,以便能夠對它們進行歸檔解檔。但是,在Core Data中,我們使用了不同方式,不需要創建一個新子類,而是先在數據模型中創建實體(Entity),然後在代碼中為這些實體創建托管對象(Managed Object) 實體,就是對對象的描述;   托管對象,表示在運行的過程該實體的具體實例; (可以這麼理解:實體、托管對象之間的關係類似於類與類的對象;)   2、鍵-值編碼形式 在我們使用NSDictionary的時候,就已經使用到這種編碼的形式了,但與NSDictionary相比,Core Data會複雜一些,只是基本概念是相同的。具體的操作方法如下: 首先定義一個托管對象: NSManagedObject *managedObject; 那麼,就可以通過相應的方法獲取name特性的數據值了:
NSString *nameData = [managedObject valueForKey:@"name"];
為name特性設置新的屬性值:
[managedObject setValue:@"newNameData" forKey:@"name"];

 

3、動手:模型的創建。

在左邊的項目導航面板上面單擊“persistence4.xcdatamodeld”文件,此時打開了Xcode的數據模型編輯器,編輯器的面板中已經列出了數據模型中的所有實體、獲取請求和配置。

由於我們還未創建數據模型,因此列表是空的,單擊實體面板左下方的加號圖標(Add Entity),此時創建了一個名為:“Entity”的實體:

(提醒一下的是,右下角的“Editor Style”選項:table視圖和graph視圖。這兩種視圖在數據模型上沒有區別,只是顯示的方式不同而已。如果你的模型裡面包含多個實體,那麼graph視圖的顯示方式會非常有用,它以圖形化的方式呈現了所有實體之間的關係;由於table視圖顯示了當前實體更為詳細的信息,因為我們在創建這個實體的時候,還是選用預設的table實體)

 

然後點擊該實體,在右邊的數據模型編輯器上面,把第一個name欄位改為我們接下來使用的“Line”欄位,所以我們這樣就算創建了一個名為“Line”的實體了。

 

接下來就為“Line”實體添加新特性,單擊並按住右下角的加號圖標“Add Attribute”,當然添加特性的話也可以直接點擊“+”圖標就可以了,這裡只是為了方便讀者看到該選項所表達的意思。

 

點擊“+”後,可以看到新增了一個名為“attribute”的特性,把它修改為“lineNumber”,修改Type為“Interger16”,並把右邊圈紅的Optional取消選中狀態。

 

再次單擊“+”,把新特性修改為“lineText”,修改Type為“String”,這裡的Optional預設勾選(該選項用於防止我們創建的“lineText”文本在用戶給定的欄位為空,而“lineNumber”表行號,行號不會出現為空的情況,)

下麵是代碼部分,與SQLite的創建類似:

在“Main.storyboard”中拖入4個標簽、4個文本框控制項,拖動並對齊標簽與文本框,並依次修改標簽文本如【圖1】,“ViewController.h”中添加一個裝載4個文本框的數組“lineFields

#import <UIKit/UIKit.h>
@interface ViewController : UIViewController

@property (nonatomic,strong)IBOutletCollection(UITextField) NSArray *lineFields; //存儲4個文本框欄位的數組

@end

然後打開輔助編輯器,通過control鍵將4個文本框連接到 lineFields 這個數組,確保連接順序為從頂部到底部!

單擊“AppDelegate.h”,我們能夠已經包含了數據類型定義需要的代碼了,我們做一些註釋:

//COREDATA托管上下文
@property (readonly, strong, nonatomic) NSManagedObjectContext *managedObjectContext;
//托管模型
@property (readonly, strong, nonatomic) NSManagedObjectModel *managedObjectModel;
//存儲時(持久化)協調者
@property (readonly, strong, nonatomic) NSPersistentStoreCoordinator *persistentStoreCoordinator;
//保存托管上下文
- (void)saveContext;
//取得當前應用程式文檔路徑
- (NSURL *)applicationDocumentsDirectory;

 點擊“ViewController.m”,下麵,我們進行一連串的代碼:

 1 #import "ViewController.h"
 2 #import "AppDelegate.h"     //需要導入app代理類
 3 
 4 static NSString *const Zline       = @"Line";
 5 static NSString *const ZlineNumber = @"lineNumber";
 6 static NSString *const ZlineText   = @"lineText";
 7 
 8 @implementation ViewController
 9 
10 - (void)viewDidLoad {
11     [super viewDidLoad];
12     //獲取應用程式代理
13     AppDelegate *appDe = [UIApplication sharedApplication].delegate;
14     //獲取托管對象上下文(此時如果資料庫不存在就不會創建資料庫)
15     NSManagedObjectContext *context = [appDe managedObjectContext];
16     //創建請求(並傳遞實體描述“line”給它)
17     NSFetchRequest *request = [[NSFetchRequest alloc]initWithEntityName:Zline];
18     //通過上下文context執行請求request,獲取記錄對象的數組
19     NSArray *objetcs  = [context executeFetchRequest:request error:nil];
20     if(objetcs == nil)  //確保返回的是有效的數組
21     {
22         NSLog(@"數組創建失敗");
23     }
24     //分別提取每個托管對象保存的數據
25     for(NSManagedObject *managed in objetcs)
26     {
27         //獲取行號(註意轉換為int)
28         int lineNum = [[managed valueForKey:ZlineNumber] intValue];
29         //獲取文本
30         NSString *lineText = [managed valueForKey:ZlineText];
31         
32         UITextField *textField = self.lineFields[lineNum];
33         textField.text = lineText;
34     }
35 
36     //後臺處理
37     UIApplication *app = [UIApplication sharedApplication];
38     [[NSNotificationCenter defaultCenter]addObserver:self selector:@selector(applicationWillResignActiveNotification:) name:
UIApplicationWillResignActiveNotification object:app]; 39 } 40 41 -(void)applicationWillResignActiveNotification:(NSNotification *)notification 42 { 43 AppDelegate *appDe = [UIApplication sharedApplication].delegate; 44 NSManagedObjectContext *context = appDe.managedObjectContext; 45 46 for(int i =0;i<4;i++) 47 { 48 NSFetchRequest *request = [[NSFetchRequest alloc]initWithEntityName:Zline]; 49 //predicate謂語,創建請求,但是為確認存儲中是否已有一個與欄位對應的托管對象,創建謂語,是為了給欄位標識正確的對象。 50 request.predicate = [NSPredicate predicateWithFormat:@"(lineNumber=%d)",i]; //註意謂語的拼寫:@"(lineNumber = %d)",i 51 NSArray *objects = [context executeFetchRequest:request error:nil]; 52 if(objects ==nil) 53 { 54 NSLog(@"數組創建失敗"); 55 } 56 57 //因為我們不知道是要從存儲中載入托管對象,還是創建新的托管對象,因此先創建空的托管對象 58 NSManagedObject *managed = nil; 59 if([objects count]>0) //檢查返回有效的對象,因此載入 60 { 61 managed = [objects objectAtIndex:0]; 62 } 63 else //檢查到無有效對象,因此創建新的托管對象 64 { 65 //創建實體、插入托管對象到獲取的上下文,我們直接用下麵這句代碼,省去很多流程 66 managed = [NSEntityDescription insertNewObjectForEntityForName:Zline inManagedObjectContext:context]; 67 } 68 UITextField *textField = self.lineFields[i]; 69 //使用鍵-值碼方式更新設置行號和文本: 70 [managed setValue:[NSNumber numberWithInt:i] forKey:ZlineNumber]; 71 [managed setValue:textField.text forKey:ZlineText]; 72 } 73 //完成迴圈。 74 //最後一步:持久化數據: 75 [appDe saveContext]; 76 } 77 78 @end

我們解析一下上面的代碼,首先需要導入我們創建Core Data模型時Xcode創建的已有代碼的“AppDelegate.h”。

(4-6行)    :定義包括實體“Line”、行號“lineNumber”、文本“lineText”等的字元段,方便我們後面的代碼編寫;(記得別拼錯,別問我為什麼怎麼說...我就是剛剛在演示的時候一直報錯,才發現原來只是字元串拼錯了...555..心疼啊左);

(12-23行): 通過上下文context,執行請求request獲取記錄對象的數組。並確認數組有效。

(24-34行):分別提取每個托管對象保存的數據,並賦值給對應行號的文本框文本欄位;

(36-39行):後臺處理

(48-55行):執行帶有謂語的請求。

(57-71行):分托管對象是否已經存在2種情況,進行編碼設置行號和文本

(75行):     持久化數據(記得帶上這行代碼)

 

好了,關於Core Data數據模型和GUI界面,以及代碼我們已經設計編寫完畢。

按“command+R”運行程式,為4個文本框輸入欄位,關閉Xcode,或按下“command+shift”,點擊2次“H”鍵,退出該應用,然後再次打開, 如果運行沒有發生錯誤的話,那麼我們已經設計了一個簡單的Core Data儲存數據應用“persistence4”了。       至此,我們包括上文iOS開發中的4種數據持久化方式【一、屬性列表與歸檔解檔】的演練,已經為大家展示了有關iOS開發中的4種數據持久化方式。 希望能夠分享與讀者。 只是,對於這兩篇關於iOS開發數據持久化的所搭建的應用"persistence"例子,也只是一個簡單的應用,具體的應用設計大家可以發揮創造力,讓數據持久化在移動開發應用過程中更加便捷。 當然,更多更深入的數據持久化、數據處理,我們只懂得這些是遠遠不夠的,需要我們通過網路上共用的內容以及自己工作學習中不斷積累,才能使這些知識點更加深入,更加適應iOS開發工作。  
您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 當系統版本號高於iOS7.0,那麼原來的隱藏狀態欄方式就可能不好使了. 因為你要是用修改plist的方法實現的隱藏方法,還是管用的. plist方法: key:Status bar is initially hidden value : YES 自從開啟程式,狀態欄就被隱藏了 key:View co
  • adapter.notifyDataSetChanged();
  • 最近做android開發遇到無法通過usb鏈接設備的情況,通過wifi連接設備調試也頗為方便 1、android 要root , 下載終端app 比如 BetterTerminal 2、通過以下命令開啟adbd su //如果前面顯示的符號是$ ,則運行此命令切換到root。如果是# ,可以不用此命
  • 有些項目用xcode7打開運行,打包安裝到iOS9設備上程式會閃退。如果用xcode7以下編譯,然後打包到iOS9的設備上就是正常的。這是為什麼,關鍵是,怎麼解決? 答:iOS9發佈之後,有些app在新的系統下會經常出現閃退的情況,而官方也給了許多的適配與改變。以使用戶體驗更好。所以做為開發者怎樣為
  • 一、前言 android客戶端開發進入尾聲,負責SEO同事突然發給我一個涉及45個發佈渠道的噩耗,之前只發佈自有渠道的工作方式已經不滿足需求,所以引入最近比較流行的gradle打包技術。 gradle基於groovy語言,引入的原因也方便了以後從現在使用的eclipse開發環境遷移到Android
  • 昨天花了一下午的時間研究了下極光推送,也前也是沒做過,不知道從何下手!才開始的時候一看官方的SDK感覺好難,不過經過一系列的搗鼓之後,手機收到了推送信息,感覺其實並沒有那麼難! 1.配置開發證書(得有開發者賬號,個人,企業的都可以) 開發環境測試 在對 JPush iOS 開發環境進行測試前,請確保
  • 我們經常需要把一個數字轉成字元串,當你不需要配合其他字元串的時候可以用description. 1 /** 2 description屬於NSObject 3 值是NSNumber時候,不用stringWithFormate來轉化成字元串了.簡便得多 4 在解析/賦值的時候比較有用,當我們需要NSS
  • public class ButtonUtils { private static long lastClickTime; public synchronized static boolean isFastClick() { long time = System.currentTimeMillis(
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...