1

I have a problem with reading a file using swift. I have searched a lot on the web to se if i can find anything, I found 3 different, but I can't get any of them to work

here they are :

    import Foundation


//----- 1 ------
var error: NSErrorPointer = nil

let url = NSURL(string: "ISO.csv")
let csvString = String(contentsOfURL:url!, encoding: NSUTF8StringEncoding, error: error);


println("contest")
println(csvString)


//----- 2 ------
func readFile(fileName: String, fileType: String) -> String{
    var fileRoot = NSBundle.mainBundle().pathForResource(fileName, ofType: fileType)
    var contents = NSString.stringWithContentsOfFile(fileRoot!, encoding: NSUTF8StringEncoding, error: nil)
    return contents
}

// example: read file.txt
var contents = readFile("ISO", "csv")
println(contents)


//----- 3 -----

let path = NSBundle.mainBundle().pathForResource("ISO", ofType: "csv")
var data = String.stringWithContentsOfFile(path, encoding: NSUTF8StringEncoding, error: nil)

in number 1 : it just returns a nil. but it works with returning data from a website

number 2: /ISO/main.swift:26:20: 'String.Type' does not have a member named 'stringWithContentsOfFile'

number 3 : /ISO/main.swift:38:21: 'stringWithContentsOfFile(_:encoding:error:)' is unavailable: use object construction 'NSString(contentsOfFile:encoding:error:)'

i have no idea what to do, and hoped some of you knew, thanks in advance

Andy
  • 35
  • 1
  • 5

3 Answers3

1
//----- 2 ------
func readFile(fileName: String, fileType: String) -> String{
    var fileRoot = NSBundle.mainBundle().pathForResource(fileName, ofType: fileType)
    var contents = NSString.stringWithContentsOfFile(fileRoot!, encoding: NSUTF8StringEncoding, error: nil)
    return contents
}

// example: read file.txt
var contents = readFile("ISO", "csv")
println(contents)


//----- 3 -----

let path = NSBundle.mainBundle().pathForResource("ISO", ofType: "csv")
var data = String.stringWithContentsOfFile(path, encoding: NSUTF8StringEncoding, error: nil)

Both of these are using the wrong intializer syntax, as the error states. They also do the same exact thing.

Fix:

let path = NSBundle.mainBundle().pathForResource("ISO", ofType: "csv")
var data = String(contentsOfFile:path, encoding: NSUTF8StringEncoding, error: nil)
Jack
  • 16,677
  • 8
  • 47
  • 51
  • 1
    This is because in XCode 6.1, initializers can now fail, so Apple changed a lot of "class funcs" to initializers. Some of the samples on the web is still olding the pre-6.1 functions. See https://developer.apple.com/library/ios/releasenotes/DeveloperTools/RN-Xcode/Chapters/xc6_release_notes.html – tng Dec 04 '14 at 18:50
  • @Andy That is most likely because `path` is `nil`. Are you sure the filename and type are correct and that the file is added into the bundle? – Jack Dec 04 '14 at 19:10
  • @JackWu , I'm pretty sure, i have tried some different path'es, and all of them i tried drag and drop – Andy Dec 04 '14 at 19:18
1

You may find this tool useful: https://github.com/shoumikhin/StreamScanner

So to parse your file you do:

import StreamScanner

if let input = NSFileHandle(forReadingAtPath: NSBundle.mainBundle().pathForResource("ISO", ofType: "csv"))
{
    let scanner = StreamScanner(source: input, delimiters: NSCharacterSet(charactersInString: ",\n"))

    //EITHER

    while
        let field: String = scanner.read() //read CSV field by field, skipping newlines
    {
        //work with field
    }

    //OR

    while  //parse each line at a time (if you're sure there're enough fields in each line and you even know their types)
        let field1: String = scanner.read(),
        let field2: Int = scanner.read(),
        let field3: Double = scanner.read(),
        {
            //work with fields
        }
}

Hope, this helps.

shoumikhin
  • 1,327
  • 15
  • 23
1

Swift 3.0 version:

let path = Bundle.main.url(forResource: FileNameWithoutExtension, withExtension: FileExtension) 
do {
            let content = try String(contentsOf: path!, encoding: .utf8)
            print(content)
} catch  {
            print("Error:file content can't be loaded")
}
Bono Lv
  • 577
  • 5
  • 7