stringByAppendingPathComponent недоступний


132

Моя програма ділиться фотографією в Instagram, для цього спочатку зберігає її у тимчасовому каталозі:

let writePath = NSTemporaryDirectory().stringByAppendingPathComponent("instagram.igo")

Він працював над Swift 1.2, але не працює Swift 2.0.

Повідомлення про помилку:

stringByAppendingPathComponent недоступний: замість цього використовуйте URLByAppendingPathComponent в NSURL.

Відповіді:


145

Схоже, метод stringByAppendingPathComponentвидалено у Swift 2.0, тому те, що пропонує повідомлення про помилку, полягає у використанні:

let writePath = NSURL(fileURLWithPath: NSTemporaryDirectory()).URLByAppendingPathComponent("instagram.igo")

Оновлення:

URLByAppendingPathComponent()замінено на appendingPathComponent()так, замість цього:

let writePath = NSURL(fileURLWithPath: NSTemporaryDirectory()).appendingPathComponent("instagram.igo")

якщо ви збираєтеся використовувати цей дизайн, у вас виникнуть проблеми, як перетворити простір на% 20Application%20Support
Роман

ні, Swift 2.0 може використовувати stringByAppendingPathComponent, дивіться мою відповідь нижче.
Джеффрі Нео

2
@JeffreyNeo так, але це не NSURLметод, аNSString
Dániel Nagy

@ DánielNagy Я маю на увазі, що ви сказали, що " stringByAppendingPathComponentвидалено в Swift 2.0", це невірно, і @Maysam не запитував лише NSURLметод.
Джеффрі Нео

4
@JeffreyNeo насправді це правильно, оскільки в String Swift 1.2 був метод, який називається stringByAppendingPathComponent, але String Swift 2.0 ні. І NSString не є частиною мови Swift, це частина основи Foundation.
Даніель Надь

75

Він працює для того, NSStringщоб ви могли використовувати його так:

extension String {
    func stringByAppendingPathComponent(path: String) -> String {
        let nsSt = self as NSString
        return nsSt.stringByAppendingPathComponent(path)
    }
}

Тепер ви можете використовувати це розширення , яке буде конвертувати ваші Stringв NSStringпершу , а потім виконати операцію.

І ваш код буде:

let writePath = NSTemporaryDirectory().stringByAppendingPathComponent("instagram.igo")

Ось ще кілька методів використання:

extension String {  

    var lastPathComponent: String {  
        return (self as NSString).lastPathComponent  
    }  
    var pathExtension: String {  
        return (self as NSString).pathExtension  
    }  
    var stringByDeletingLastPathComponent: String {  
        return (self as NSString).stringByDeletingLastPathComponent  
    }  
    var stringByDeletingPathExtension: String {  
        return (self as NSString).stringByDeletingPathExtension  
    }  
    var pathComponents: [String] {  
        return (self as NSString).pathComponents  
    }  
    func stringByAppendingPathComponent(path: String) -> String {  
        let nsSt = self as NSString  
        return nsSt.stringByAppendingPathComponent(path)  
    }  
    func stringByAppendingPathExtension(ext: String) -> String? {  
        let nsSt = self as NSString  
        return nsSt.stringByAppendingPathExtension(ext)  
    }  
}

Посилання з ТУТ .

Для швидкого 3.0:

extension String {
    func stringByAppendingPathComponent1(path: String) -> String {
        let nsSt = self as NSString
        return nsSt.appendingPathComponent(path)
    }
}

let writePath = NSTemporaryDirectory().stringByAppendingPathComponent(path: "instagram.igo")


extension String {

    var lastPathComponent: String {
        return (self as NSString).lastPathComponent
    }
    var pathExtension: String {
        return (self as NSString).pathExtension
    }
    var stringByDeletingLastPathComponent: String {
        return (self as NSString).deletingLastPathComponent
    }
    var stringByDeletingPathExtension: String {
        return (self as NSString).deletingPathExtension
    }
    var pathComponents: [String] {
        return (self as NSString).pathComponents
    }
    func stringByAppendingPathComponent(path: String) -> String {
        let nsSt = self as NSString
        return nsSt.appendingPathComponent(path)
    }
    func stringByAppendingPathExtension(ext: String) -> String? {
        let nsSt = self as NSString
        return nsSt.appendingPathExtension(ext)
    }
}

12
Хоча це правильне рішення, є причина, чому Apple усунула ці методи - використання шляхів до локалізації ресурсів застаріле, і NSURLзамість них слід використовувати. Просто кажу.
Чарлі Монро

snippet: String (NSString (рядок: шлях) .stringByAppendingPathComponent (imageName)) ... в іншому випадку цілком погоджується з @CharlieMonroe
Bobjt

1
@CharlieMonroe, якщо це дійсно так, чому в SDK все ще існує маса методів, які не сприймають URL-адресу як шлях?
Joris Mans

@JorisMans Це, як правило, більш старі методи (доступні з 10.0 або раніше). З тих пір, як пісочниця була введена, немає способу пройти шлях, наприклад, із закладкою appscope - вам потрібна URL-адреса. Apple повільно оновлює API, якими користуються лише декілька людей. Або у вас є приклад нещодавно доданого API (останні 3-4 роки)?
Чарлі Монро

1
@IulianOnofrei - Тому що ви повинні використовувати checkResourceIsReachable()або checkPromisedItemIsReachable()на URLзамість. FileManagerяк і раніше клас ObjC NSFileManagerз NSпрефіксом, видаленим для Swift, і чи fileExistsAtPathіснував він ще з OS X 10.0. Світ розвинувся з тих пір, і оскільки програми перебувають у пісочному режимі (що менш очевидно в iOS), файл може існувати, ви просто не можете мати дозвіл на його перегляд; також, файл може знаходитись у хмарі тощо. Ось чому простий BOOLметод замінюється чимось складнішим URL, але більш семантично правильним.
Чарлі Монро

30

Просто оберніть рядок як NSString.

let writePath = (NSTemporaryDirectory() as NSString).stringByAppendingPathComponent("instagram.igo")

класний .. Stringклас не має цього, але NSStringіснує! має сенс.
preetam

16

для Swift 3 :

let writePath = URL(fileURLWithPath: NSTemporaryDirectory()).appendingPathComponent(directoryname).path

або краще створити це розширення:

extension String {
    func appendingPathComponent(_ string: String) -> String {
        return URL(fileURLWithPath: self).appendingPathComponent(string).path
    }
}

використання:

 let writePath = NSTemporaryDirectory().appendingPathComponent(directoryname)

6

Рішення Swift 3:

Ось функція отримати шлях до каталогу директорій-

    func getDocumentsDirectory() -> URL {
         let paths = FileManager.default.urls(for: .documentDirectory, in:.userDomainMask)
         let documentsDirectory = paths[0]
         return documentsDirectory
     }

Як використовувати:

    getDocumentsDirectory.appendingPathComponent("google.com")

Результат:

    file:///var/folders/w1/3rcp2fvs1qv43hfsh5876s0h0000gn/T/com.apple.dt.Xcode.pg/containers/com.apple.dt.playground.stub.iOS_Simulator.MyPlayground-7CF9F706-509C-4D4C-997E-AB8FE9E4A6EA/Documents/google.com

5

Для швидкого 2.0

// Get the documents Directory
    func documentsDirectory() -> String {
        let documentsFolderPath = NSSearchPathForDirectoriesInDomains(NSSearchPathDirectory.DocumentDirectory, NSSearchPathDomainMask.UserDomainMask, true)[0]
        return documentsFolderPath
    }

// Get path for a file in the directory
func fileInDocumentsDirectory(filename: String) -> String {

    let writePath = (documentsDirectory() as NSString).stringByAppendingPathComponent("Mobile")

    if (!NSFileManager.defaultManager().fileExistsAtPath(writePath)) {
        do {
            try NSFileManager.defaultManager().createDirectoryAtPath(writePath, withIntermediateDirectories: false, attributes: nil) }
            catch let error as NSError {
                print(error.localizedDescription);
        }
    }
    return (writePath as NSString).stringByAppendingPathComponent(filename)
}

//# MARK: - Save Image in Doc dir
func saveImage (image: UIImage, path: String ) -> Bool{

    let pngImageData = UIImagePNGRepresentation(image)
    //        let jpgImageData = UIImageJPEGRepresentation(image, 1.0)   // if you want to save as JPEG
    let result = pngImageData!.writeToFile(path, atomically: true)

    print("\(result)")
    print("\(path)")

    return result

}

2

Ви можете використовувати URLByAppendingPathComponent () замість цього. Зверніть увагу, що вам слід обрізати рядок шляху, щоб видалити префікс "file: //":

let uniqueFileName = NSUUID().UUIDString
let documentsDirectory = getDocumentsDirectoryURL()
    if let path = documentsDirectory?.URLByAppendingPathComponent(uniqueFileName) {
        var pathString = path.absoluteString
        pathString = imagePathString.stringByTrimmingCharactersInSet(NSCharacterSet(charactersInString: "file://"))
}

func getDocumentsDirectoryURL() -> NSURL? {
    let fileManager = NSFileManager()
    if let docsDirectory = fileManager.URLsForDirectory(.DocumentDirectory, inDomains: .UserDomainMask).first {
        return docsDirectory
    }
    return nil
}


0

Я спробував це, і це вирішило проблему.

перед:

let localPath = documentDirectory.URLByAppendingPathComponent(imageName)

після:

let localPath = (documentDirectory as NSString).appendingPathComponent(imageName)

-1

Якщо використання NSStringметодів шляху (замість Stringметодів URL) є прийнятним, набагато простіше розширити Stringобчислену властивість або метод, що повертає його значення як NSString(замість дублювання потрібних методів у Stringрозширенні):

extension String
{
    var ns: NSString { return self as NSString }
}

і потім:

swiftStringPath.ns.appendingPathComponent("whateva")
swiftStringPath.ns.deletingPathExtension

-2

Швидкий 4

extension String {

    var lastPathComponent: String {
        return (self as NSString).lastPathComponent
    }
    var pathExtension: String {
        return (self as NSString).pathExtension
    }
    var stringByDeletingLastPathComponent: String {
        return (self as NSString).deletingLastPathComponent
    }
    var stringByDeletingPathExtension: String {
        return (self as NSString).deletingPathExtension
    }
    var pathComponents: [String] {
        return (self as NSString).pathComponents
    }
    func stringByAppendingPathComponent(path: String) -> String {
        let nsSt = self as NSString
        return nsSt.appendingPathComponent(path)
    }
    func stringByAppendingPathExtension(ext: String) -> String? {
        let nsSt = self as NSString
        return nsSt.appendingPathExtension(ext)
    }
}
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.