Ios 以NSException Parse server类型的未捕获异常终止

Ios 以NSException Parse server类型的未捕获异常终止,ios,swift,compiler-errors,Ios,Swift,Compiler Errors,我有一个名为“fetchPosts”的函数,当我将此函数添加到任何其他方法(如view Dod Display)或制作一个按钮以更新我获取的视图时,它将数据从解析服务器提取到UicollectionViewController” 以NSException类型的未捕获异常终止 “不知道这里有什么问题 import UIKit import AVKit import AVFoundation import CoreLocation import Parse class NewsfeedCollec

我有一个名为“
fetchPosts
”的函数,当我将此函数添加到任何其他方法(如view Dod Display)或制作一个按钮以更新我获取的视图时,它将数据从解析服务器提取到
UicollectionViewController

以NSException类型的未捕获异常终止

“不知道这里有什么问题

import UIKit
import AVKit
import AVFoundation
import CoreLocation
import Parse

class NewsfeedCollectionViewController : UICollectionViewController, CLLocationManagerDelegate
{
    var searchController: UISearchController!
    var posts: [Post]?

    override func viewDidLoad() {
        super.viewDidLoad()

        if let user = PFUser.current() {
            PFGeoPoint.geoPointForCurrentLocation { (geopoint, error) in
                if geopoint != nil {
                    let geo = geopoint
                    user["location"] = geo
                    user.saveInBackground()
                }
            }
        }

        self.fetchPosts()
        collectionView?.contentInset = UIEdgeInsets(top: 12, left: 4, bottom: 12, right: 4)

        if let layout = collectionView?.collectionViewLayout as? PinterestLayout {
            layout.delegate = self
        }
    }

    func fetchPosts()
    {
        DispatchQueue.global(qos: .userInteractive).async {
            self.posts = Post.fetchPosts(viewController: self)

            DispatchQueue.main.async {
                self.collectionView?.reloadData()
            }
        }
    }



    @IBAction func reloadbtnPressed(_ sender: Any) {
        fetchPosts()
    }


}

extension NewsfeedCollectionViewController
{
    override func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int {
        if let posts = posts {
            return posts.count
        } else {
            return 0
        }
    }

    override func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell
    {
        let cell = collectionView.dequeueReusableCell(withReuseIdentifier: "PostCell", for: indexPath) as! PostCollectionViewCell
        cell.post = self.posts?[indexPath.item]
        return cell
    }
}

extension NewsfeedCollectionViewController : PinterestLayoutDelegate
{
    func collectionView(collectionView: UICollectionView, heightForPhotoAt indexPath: IndexPath, with width: CGFloat) -> CGFloat
    {
        if let post = posts?[indexPath.item], let _ = post.image {
            let boundingRect = CGRect(x: 0, y: 0, width: width, height: CGFloat(MAXFLOAT))
//            do {
//                try postImageView.image = UIImage(data: image!.getData())
//            }
//            catch {
//
//            }
            do {
                var image: UIImage
                try image = UIImage(data: post.image!.getData())!
                let rect = AVMakeRect(aspectRatio: image.size, insideRect: boundingRect)
                return rect.size.height
            }
            catch {
                return 1;
            }

        }

        return 0
    }

    func collectionView(collectionView: UICollectionView, heightForCaptionAt indexPath: IndexPath, with width: CGFloat) -> CGFloat
    {
        if let post = posts?[indexPath.item] {
            let topPadding = CGFloat(8)
            let bottomPadding = CGFloat(12)
            let captionFont = UIFont.systemFont(ofSize: 15)
            let captionHeight = self.height(for: post.caption!, with: captionFont, width: width)
            let profileImageHeight = CGFloat(36)
            let height = topPadding + captionHeight + topPadding + profileImageHeight + bottomPadding

            return height
        }

        return 0.0
    }

    func height(for text: String, with font: UIFont, width: CGFloat) -> CGFloat
    {
        let nsstring = NSString(string: text)
        let maxHeight = CGFloat(64.0)
        let textAttributes = [NSFontAttributeName : font]
        let boundingRect = nsstring.boundingRect(with: CGSize(width: width, height: maxHeight), options: .usesLineFragmentOrigin, attributes: textAttributes, context: nil)
        return ceil(boundingRect.height)
    }
}

extension NewsfeedCollectionViewController : PostProtocol
{
    func didFinishFetch(posts: [Post]?)
    {
        if (posts != nil) {
            self.posts = posts
        }
        self.collectionView?.reloadData()
    }
}
下面是我用来从服务器获取数据的模型Post文件:

import UIKit
import Parse

protocol PostProtocol: class {
    func didFinishFetch(posts: [Post]?)
}

struct Post
{
    var ID: String
    var createdBy: User
    var timeAgo: String?
    var caption: String?
//    var image: UIImage?
    var image: PFFile?
    var numberOfLikes: Int?
    var numberOfComments: Int?
    var numberOfShares: Int?

    static weak var delegate: PostProtocol?

    static func fetchPosts(viewController: PostProtocol) -> [Post]
    {
        var posts = [Post]()
        delegate = viewController

        let query = PFQuery(className: "posts");
        if let latitude = (PFUser.current()?["location"] as AnyObject).latitude {
            if let longitude = (PFUser.current()?["location"] as AnyObject).longitude {
                let geoPoint = PFGeoPoint(latitude: latitude, longitude: longitude)
                query.whereKey("postLocation", nearGeoPoint: geoPoint, withinKilometers: 1)
            }
        }
        query.findObjectsInBackground { (objects: [PFObject]?, error: Error?) in
            if error == nil {
                for object in objects! {
                    let pfObject = object as PFObject
                    let ID = pfObject["uuid"] as! String
                    let caption = pfObject["title"] as! String
                    let likes = pfObject["likes"] as? Int
                    let comments = pfObject["comments"] as? Int
                    let shares = pfObject["shares"] as? Int
                    let image = pfObject["pic"] as? PFFile

                    let profileImage = pfObject["ava"] as? PFFile
                    let username = pfObject["username"] as? String
                    let user = User(username: username, profileImage: profileImage);

                    let from = pfObject.createdAt
                    let now = Date()
                    let components : NSCalendar.Unit = [.second, .minute, .hour, .day, .weekOfMonth]
                    let difference = (Calendar.current as NSCalendar).components(components, from: from! as Date, to: now, options: [])
                    var timeAgo: String = ""
                    // logic what to show: seconds, minuts, hours, days or weeks
                    if difference.second! <= 0 {
                        timeAgo = "now"
                    }
                    if difference.second! > 0 && difference.minute! == 0 {
                        timeAgo = "\(difference.second!)s."
                    }
                    if difference.minute! > 0 && difference.hour! == 0 {
                        timeAgo = "\(difference.minute!)m."
                    }
                    if difference.hour! > 0 && difference.day! == 0 {
                        timeAgo = "\(difference.hour!)h."
                    }
                    if difference.day! > 0 && difference.weekOfMonth! == 0 {
                        timeAgo = "\(difference.day!)d."
                    }
                    if difference.weekOfMonth! > 0 {
                        timeAgo = "\(difference.weekOfMonth!)w."
                    }

                    let post = Post(ID: ID, createdBy: user, timeAgo: timeAgo, caption: caption, image: image, numberOfLikes: likes, numberOfComments: comments, numberOfShares: shares)
                    posts.append(post);
                }
                delegate?.didFinishFetch(posts: posts)
            }
        }


        return posts
    }
}

struct User
{
    var username: String?
    var profileImage: PFFile?
}
导入UIKit
导入解析
协议后协议:类{
func didfishfetch(posts:[Post]?)
}
结构柱
{
变量ID:String
var createdBy:User
var timeAgo:字符串?
变量标题:字符串?
//var图像:UIImage?
var图像:PFFile?
var numberOfLikes:Int?
var numberOfComments:Int?
var numberOfShares:Int?
静态弱var委托:后协议?
静态函数fetchPosts(viewController:PostProtocol)->[Post]
{
var posts=[Post]()
委托=视图控制器
let query=PFQuery(类名:“posts”);
如果让纬度=(PFUser.current()?[“location”]作为任何对象)。纬度{
如果让经度=(PFUser.current()?[“location”]作为任何对象)。经度{
let geoPoint=PFGeoPoint(纬度:纬度,经度:经度)
query.whereKey(“postLocation”,nearGeoPoint:geoPoint,withinKilometers:1)
}
}
query.findObjectsInBackground{(对象:[PFObject]?,错误:error?)位于
如果错误==nil{
对于对象中的对象{
将pfObject=对象设为pfObject
让ID=pfObject[“uuid”]作为!字符串
将caption=pfObject[“title”]设为!字符串
让likes=pfObject[“likes”]as?Int
将comments=pfObject[“comments”]设为?Int
将shares=pfObject[“shares”]设为?Int
将image=pfObject[“pic”]设为PFFile
将profileImage=pfObject[“ava”]设为?PFFile
将username=pfObject[“username”]设为?字符串
让user=user(用户名:username,profileImage:profileImage);
let from=pfObject.createdAt
让我们现在=日期()
let组件:NSCalendar.Unit=[.second、.minute、.hour、.day、.weekOfMonth]
让差异=(Calendar.current作为NSCalendar)。组件(组件,from:from!作为日期,to:now,选项:[])
var timeAgo:String=“”
//逻辑显示:秒、分钟、小时、天或周
如果difference.second!0&&difference.minute!==0{
timeAgo=“\(差。秒!)s。”
}
如果difference.minute!>0&&difference.hour!==0{
timeAgo=“\(差。分钟!)m。”
}
如果difference.hour!>0&&difference.day!==0{
timeAgo=“\(差。小时!)h。”
}
如果difference.day!>0&&difference.weekOfMonth!==0{
timeAgo=“\(差异.天!)d。“
}
如果差异.weekOfMonth!>0{
timeAgo=“\(差异。周/月!)w。“
}
让post=post(ID:ID,createdBy:user,timeAgo:timeAgo,caption:caption,image:image,numberOfLikes:likes,numberOfComments:comments,numberOfShares:shares)
职位。追加(职位);
}
代理?.didfishfetch(posts:posts)
}
}
返回岗位
}
}
结构用户
{
var用户名:字符串?
var profileImage:PFFile?
}

1)能否提供UIImage的getData()方法的代码?看起来它是UIImage扩展中的一个方法。2) 为什么称之为:try image=UIImage(数据:post.image!.getData())!我尝试了image post.image,但出现了一个错误,无法将image类型转换为PFFile类型。open func getData()抛出->Data/**此方法类似于
-getData
,但避免将整个
PFFile
内容一次保存在内存中@指向将在必要时设置的
n错误的param error指针@返回包含数据的流。如果提取时出错,则返回nil*/尝试检查数据是否可用并打印异常错误:if post.image?.isDataAvailable{var image:UIImage?do{let data=try post.image?.getData()image=UIImage(data:data)}catch{print(“发生错误:(error.localizedDescription)“}}我已经这样做了,但是我仍然得到了相同的错误!问题是函数“fetchPosts”在我用于ViewDidLoad时工作正常,并且它实际上在CollectionVIew上加载了文章,但是当我尝试在任何其他方法中重用时,我得到了这个错误。你能提供错误描述吗?