Swift开发报错:类型'[ListB]'无'books'成员问题求助
问题解决:Value of type '[ListB]' has no member 'books'
问题场景
执行fetchAPIDataTop100FHC函数时,在books = hardfictList.books行报错:Value of type '[ListB]' has no member 'books'。相关代码如下:
报错函数代码
func fetchAPIDataTop100FHC() { let url = myUrl AF.request(url, method: .get, parameters: nil, encoding: URLEncoding.default, headers: nil, interceptor: nil) .response{ resp in switch resp.result{ case .success(let data): do{ let jsonData = try JSONDecoder().decode(NYTTop100FictionModel.self, from: data!) let hardfictList = jsonData.results.listsb.filter ({ $0.listNameEncoded == "hardcover-fiction" }) //print(jsonData.results.listsb) books = hardfictList.books } catch { print(String(describing: error)) } case .failure(let error): print(String(describing: error)) } } //end response } //end fetch API
相关结构体代码
struct Result: Decodable { let bestsellersDate: String let publishedDate: String let publishedDateDescription: String let previousPublishedDate: String let nextPublishedDate: String let listsb: [ListB] private enum CodingKeys: String, CodingKey { case bestsellersDate = "bestsellers_date" case publishedDate = "published_date" case publishedDateDescription = "published_date_description" case previousPublishedDate = "previous_published_date" case nextPublishedDate = "next_published_date" case listsb = "lists" } init(bestsellersDate: String, publishedDate: String, publishedDateDescription: String, previousPublishedDate: String, nextPublishedDate: String, listsb: [ListB]) { self.bestsellersDate = bestsellersDate self.publishedDate = publishedDate self.publishedDateDescription = publishedDateDescription self.previousPublishedDate = previousPublishedDate self.nextPublishedDate = nextPublishedDate self.listsb = listsb } } struct ListB: Decodable { let listID: Int let listName: String let listNameEncoded: String let displayName: String let updated: String let books: [Book] private enum CodingKeys: String, CodingKey { case listID = "list_id" case listName = "list_name" case listNameEncoded = "list_name_encoded" case displayName = "display_name" case updated case books } init(listID: Int, listName: String, listNameEncoded: String, displayName: String, updated: String, books: [Book]) { self.listID = listID self.listName = listName self.listNameEncoded = listNameEncoded self.displayName = displayName self.updated = updated self.books = books } } struct Book: Codable, Identifiable { let id = UUID() let ageGroup: String let amazonProductURL: URL let articleChapterLink: String let author: String let bookImage: URL? let bookImageWidth: Int? let bookImageHeight: Int? let bookReviewLink: String let bookUri: URL let btrn: String let contributor: String let contributorNote: String let createdDate: String let description: String let firstChapterLink: String let price: String let primaryIsbn10: String let primaryIsbn13: String let publisher: String let rank: Int let rankLastWeek: Int let sundayReviewLink: String let title: String let updatedDate: String let weeksOnList: Int let buyLinks: [BuyLink] private enum CodingKeys: String, CodingKey { case ageGroup = "age_group" case amazonProductURL = "amazon_product_url" case articleChapterLink = "article_chapter_link" case author case bookImage = "book_image" case bookImageWidth = "book_image_width" case bookImageHeight = "book_image_height" case bookReviewLink = "book_review_link" case bookUri = "book_uri" case btrn case contributor case contributorNote = "contributor_note" case createdDate = "created_date" case description case firstChapterLink = "first_chapter_link" case price case primaryIsbn10 = "primary_isbn10" case primaryIsbn13 = "primary_isbn13" case publisher case rank case rankLastWeek = "rank_last_week" case sundayReviewLink = "sunday_review_link" case title case updatedDate = "updated_date" case weeksOnList = "weeks_on_list" case buyLinks = "buy_links" } init(ageGroup: String, amazonProductURL: URL, articleChapterLink: String, author: String, bookImage: URL?, bookImageWidth: Int?, bookImageHeight: Int?, bookReviewLink: String, bookUri: URL, btrn: String, contributor: String, contributorNote: String, createdDate: String, description: String, firstChapterLink: String, price: String, primaryIsbn10: String, primaryIsbn13: String, publisher: String, rank: Int, rankLastWeek: Int, sundayReviewLink: String, title: String, updatedDate: String, weeksOnList: Int, buyLinks: [BuyLink]) { self.ageGroup = ageGroup self.amazonProductURL = amazonProductURL self.articleChapterLink = articleChapterLink self.author = author self.bookImage = bookImage self.bookImageWidth = bookImageWidth self.bookImageHeight = bookImageHeight self.bookReviewLink = bookReviewLink self.bookUri = bookUri self.btrn = btrn self.contributor = contributor self.contributorNote = contributorNote self.createdDate = createdDate self.description = description self.firstChapterLink = firstChapterLink self.price = price self.primaryIsbn10 = primaryIsbn10 self.primaryIsbn13 = primaryIsbn13 self.publisher = publisher self.rank = rank self.rankLastWeek = rankLastWeek self.sundayReviewLink = sundayReviewLink self.title = title self.updatedDate = updatedDate self.weeksOnList = weeksOnList self.buyLinks = buyLinks } }
错误原因
jsonData.results.listsb是[ListB]类型的数组,调用filter方法后,返回的仍然是符合条件的ListB实例组成的数组,而不是单个ListB对象。数组本身并没有books属性,只有单个ListB实例才有这个属性,因此报错。
解决方案
根据业务需求,有两种处理方式:
方式1:获取第一个符合条件的列表(推荐)
如果确定listNameEncoded == "hardcover-fiction"的列表只有一个,用first(where:)获取第一个元素,再访问其books属性,同时处理空值避免崩溃:
do{ let jsonData = try JSONDecoder().decode(NYTTop100FictionModel.self, from: data!) guard let hardfictList = jsonData.results.listsb.first(where: { $0.listNameEncoded == "hardcover-fiction" }) else { print("未找到hardcover-fiction列表") return } books = hardfictList.books } catch { print(String(describing: error)) }
方式2:合并所有符合条件列表的书籍
如果可能存在多个符合条件的列表,遍历所有结果合并书籍数组:
do{ let jsonData = try JSONDecoder().decode(NYTTop100FictionModel.self, from: data!) let hardfictLists = jsonData.results.listsb.filter({ $0.listNameEncoded == "hardcover-fiction" }) books = hardfictLists.flatMap { $0.books } } catch { print(String(describing: error)) }
内容的提问来源于stack exchange,提问作者user1233894
相关产品推荐
相关产品推荐

