[英]C struct called in Swift not being updated when it calls native code
我有一個 C 結構:
struct FastSax {
int parseErrorType;
int parserStatus;
int cacheIndex;
char* input;
int (* findOpen)(FastSax *, int);
int (* findClose)(FastSax *, int);
void (* print)(char *);
char* (* parse)(FastSax* , const char*);
};
初始化如下:
FastSax* getDefault() {
FastSax *sax = malloc(sizeof (FastSax));
sax->cacheIndex = -1;
sax->findOpen = &findOpen;
sax->findClose = &findClose;
sax->parse = & parse;
sax->hasMoreTokens = &hasMoreTokens;
sax->fetchNextToken = &fetchNextToken;
sax->print = &print;
sax->parseErrorType = PARSE_ERROR_NONE;
sax->parserStatus = PARSE_STATUS_INSUFFICIENT_DATA;
sax->input = malloc(50 * sizeof (char));
strncpy(sax->input, "", 10);
sax->input[strlen(sax->input)] = '\0';
return sax;
}
我在處理文件行的循環中調用 parse 函數。 解析函數運行並根據其輸出更新結構對象的一些屬性。
char* parse(FastSax* fs , const char *freshData) {
//parse operations on freshData
fs.cacheIndex = strlen(freshData);
fs.parserStatus = 4;
/**Parser code here**/
//not a constant string
return "the-result-of-the-parse";
}
在 Swift 中,我這樣做:
class ParserClient{
let fastSax = getDefault()
func parse(line: String) -> Int{
let ptr = fastSax
var status:Int32 = -1
let fs: FastSax = ptr!.withMemoryRebound(to: FastSax.self, capacity: 1) {
$0.pointee
}
let out = fs.parse(ptr , line)
//consume the first token
if fs.parseErrorType == PARSE_ERROR_NONE{
var token = String(cString: out)
self.delegate.endEntry(entry: token)
while true {
var _token = String(cString: fs.parse(ptr ,""))
Log.out("\(_token) , parser-status: \(fs.parserStatus)")
if fs.parserStatus == PARSE_STATUS_OK {
self.delegate.endEntry(entry: _token)
}else{
break
}
}
}else{
Log.out("Error: parser-status: \(fs.parserStatus) , error-type: \(fs.parseErrorType)")
}
return Int(fs.parserStatus)
}
}
當在 C 中調用解析器代碼時,它工作正常。
但是當從 Swift 調用時,我注意到在 while 循環的每次迭代中都沒有更新結構對象,即fs
屬性。
題:
我如何確保在調用 C 代碼時更新結構的屬性。
從 Swift 調用的結構副本與 C 使用的不同嗎?
從 Swift 調用的結構副本與 C 使用的不同嗎?
確切地。 這個
let fs: FastSax = ptr!.withMemoryRebound(to: FastSax.self, capacity: 1) {
$0.pointee
}
是制作ptr
指向的結構副本的(復雜)方法。 然后
let out = fs.parse(ptr , line)
更新ptr
指向的結構(這是之前獲得的默認結構)而不是fs
指向的結構。
你可能想要的只是
let out = fastSax!.pointee.parse(fastSax, line)
假設fastSax
不是nil
。 如果不能保證,請使用可選綁定或可選鏈接。 不需要ptr
和fs
變量。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.