将CFURLRef或CFStringRef转换为std::string

12

如何将CFURLRef转换为C++的std::string

我还可以通过以下方式从CFURLRef转换为CFStringRef

CFStringRef CFURLGetString ( CFURLRef anURL );

但是现在我也遇到了同样的问题。我该如何将CFStringRef转换为std::string

4个回答

12

CFStringRef 是与NSString对象无缝桥接的,因此如果您以任何方式使用Cocoa或Objective C,转换非常简单:

NSString *foo = (NSString *)yourOriginalCFStringRef;
std::string *bar = new std::string([foo UTF8String]);

更多细节请参见这里

现在,既然您没有使用Cocoa或Objective-C标签,我猜您不想使用Objective-C解决方案。

在这种情况下,您需要从CFStringRef获取等效的C字符串:

const CFIndex kCStringSize = 128; 
char temporaryCString[kCStringSize];
bzero(temporaryCString,kCStringSize);
CFStringGetCString(yourStringRef, temporaryCString, kCStringSize, kCFStringEncodingUTF8);
std::string *bar = new std::string(temporaryCString);

这段代码没有进行错误检查,你可能需要通过CFStringGetCString获取的字符串进行空终止(我尝试通过bzero来缓解这个问题)。


9

这个函数可能是最简单的解决方案:

const char * CFStringGetCStringPtr ( CFStringRef theString, CFStringEncoding encoding );

当然,对于std::string(char*),有一个ctr可以为您提供这个一行代码的转换:
std::string str(CFStringGetCStringPtr(CFURLGetString(anUrl),kCFStringEncodingUTF8));

5
这个答案很简单,但最近让我吃了一些亏。我刚刚发现在文档中,CFStringGetCStringPtr 旁边的注释说:/* May return NULL at any time; be prepared for NULL */。所以,如果你使用它,要小心。 - dgross

2
最安全的实现方法如下:
CFIndex bufferSize = CFStringGetLength(cfString) + 1; // The +1 is for having space for the string to be NUL terminated
char buffer[bufferSize];

// CFStringGetCString is documented to return a false if the buffer is too small 
// (which shouldn't happen in this example) or if the conversion generally fails    
if (CFStringGetCString(cfString, buffer, bufferSize, kCFStringEncodingUTF8))
{
    std::string cppString (buffer);
}
CFStringGetCString没有像CFStringGetCStringPtr一样被记录返回NULL的情况。请确保您使用正确的CFStringEncoding类型,我认为UTF8编码应该对大多数事情都是安全的。您可以查看苹果公司有关CFStringGetCString的文档,网址为https://developer.apple.com/reference/corefoundation/1542721-cfstringgetcstring?language=objc

FYI:CFStringGetLength(cfString)返回UTF-16编码的长度。 - Marek R

1
这是我实现的转换函数:

std::string stdStringFromCF(CFStringRef s)
{
    if (auto fastCString = CFStringGetCStringPtr(s, kCFStringEncodingUTF8))
    {
        return std::string(fastCString);
    }
    auto utf16length = CFStringGetLength(s);
    auto maxUtf8len = CFStringGetMaximumSizeForEncoding(utf16length, kCFStringEncodingUTF8);
    std::string converted(maxUtf8len, '\0');

    CFStringGetCString(s, converted.data(), maxUtf8len, kCFStringEncodingUTF8);
    converted.resize(std::strlen(converted.data()));

    return converted;
}

还没有测试过。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接