It could be better to have PlayerData as a struct and not a class (no more init() needed). But that's your choice and depends on what you want to do with it.
When you read the CSV file, put it into an array of Strings, by reading each line:
If data is the String of your complete CSV file, build the array like this:
var linesOfFile : [String]
let multiLineString = data
let newlineChars = CharacterSet.newlines
linesOfFile = multiLineString.components(separatedBy: newlineChars).filter{!$0.isEmpty}
Now, read each line:
var allPlayers : [PlayerData] = []
let separatorMark = ","
for line in linesOfFile {
let aPlayerData = line.split(separator: separatorMark).map() { String($0) } // separatorMark is ","
// You get ["1", "1", "0", "Christian McCaffrey", "CAR", "RB", "13", "TRUE"]
// As you know the meaning of each you can simply fill the struct:
let num = Int(aPlayerData[0]) ?? 0
let numPosPick = Int(aPlayerData[1]) ?? -1 // May be default should be other than -1 ?
let numRookie = Int(aPlayerData[2]) ?? -1
let name = aPlayerData[3]
let team = aPlayerData[4]
let position = aPlayerData[5]
let byeWeek = Int(aPlayerData[6]) ?? 0
let isTopPlayer = aPlayerData[7] == "TRUE"
let isRookie = false // I DO NOT SEE IT IN CSV ; maybe it is computed from numRookie ? = numRookie > 0
let player = PlayerData(num: num, numPosPick: numPosPick, numRookie: numRookie, name: name, team: team, position: position, byeWeek: byeWeek, isTopPlayer: isTopPlayer, isRookie: isRookie)
allPlayers.append(player)
}
You could add a description var in your class as:
var description : String {
let topPlayer = self.isTopPlayer ? "is top player" : "plays"
return "\(self.name) \(topPlayer) in team \(team) at position: \(position) with rank: \(num), numPosPick: \(numPosPick) and numRookie: \(numRookie). His byeWeek is \(byeWeek)"
}
Calling
print(allPlayers[0].description)
yields
Christian McCaffrey is top player in team CAR at position: RB with rank: 1, numPosPick: 1 and numRookie: 0. His byeWeek is 13