2017-07-10 14 views
0

私のソケットのサーバー側から入って来るデータを自分のアプリケーション(iOS)で読み込もうとしています。私は、connectとget input関数を含むネットワーククラスを設定しました。私がNetworkEnable()関数をAppDelegateファイルのfunc application...に入れると、ソケットが接続され、サーバーは必要に応じて処理します。しかし、私のビューコントローラのコードがgetPiIn()関数に達すると、関数の最初の行にEXC_BAD_INSTRUCTIONSエラーが出ます。AppDelegateで接続するときにソケット入力を取得するときにエラーが発生する

ネットワーククラスファイル:

class Network: NSObject, StreamDelegate { 

//Socket server 
let addr = "x.x.x.x" 
let port = 2020 

var inStream : InputStream? 
var outStream: OutputStream? 

var buffer = [UInt8](repeating: 0, count: 200) 

func NetworkEnable() { 

    Stream.getStreamsToHost(withName: addr, port: port, inputStream: &inStream, outputStream: &outStream) 

    inStream?.delegate = self 
    outStream?.delegate = self 

    inStream?.schedule(in: RunLoop.current, forMode: RunLoopMode.defaultRunLoopMode) 
    outStream?.schedule(in: RunLoop.current, forMode: RunLoopMode.defaultRunLoopMode) 

    inStream?.open() 
    outStream?.open() 

    buffer = [UInt8](repeating: 0, count: 200) 


    print("Network Connected") 

} 

func stream(aStream: Stream, handleEvent eventCode: Stream.Event) { 

    switch eventCode { 
    case Stream.Event.endEncountered: 
     print("EndEncountered") 
     inStream?.close() 
     inStream?.remove(from: RunLoop.current, forMode: RunLoopMode.defaultRunLoopMode) 
     outStream?.close() 
     print("Stop outStream currentRunLoop") 
     outStream?.remove(from: RunLoop.current, forMode: RunLoopMode.defaultRunLoopMode) 

    case Stream.Event.errorOccurred: 
     print("ErrorOccurred") 

     inStream?.close() 
     inStream?.remove(from: RunLoop.current, forMode: RunLoopMode.defaultRunLoopMode) 
     outStream?.close() 
     outStream?.remove(from: RunLoop.current, forMode: RunLoopMode.defaultRunLoopMode) 

    case Stream.Event.hasBytesAvailable: 
     print("HasBytesAvailable") 

     if aStream == inStream { 
      inStream!.read(&buffer, maxLength: buffer.count) 
      let bufferStr = NSString(bytes: &buffer, length:  buffer.count, encoding: String.Encoding.utf8.rawValue) 

      print(bufferStr!) 
     } 

    case Stream.Event.hasSpaceAvailable: 
     print("HasSpaceAvailable") 

    case Stream.Event.openCompleted: 
     print("OpenCompleted") 

    default: 
     print("Unknown") 
    } 
} 

func getPiIn() -> String { 
    inStream!.read(&buffer, maxLength: buffer.count) //Error Shows up here 
    let bufferStr = NSString(bytes: &buffer, length: buffer.count, encoding: String.Encoding.utf8.rawValue) 
    return(bufferStr!) as String 
} 

相続人ViewController.Swift

getPiへの呼び出し
func changeTemp() { 

    let tempString = String(network.getPiIn()) 

    currentTemp.text = tempString 

} 

は私の推測では、ストリームの代表者が別のクラスに自己に宣言されているので、彼らがしていることですViewController.swiftではアクセスできませんが、.selfViewControllerに変更すると、ビューはロードされません。

私がnetwork.NetworkEnable()ViewDidLoad()に配置すると、そのビューを離れて戻ってくるまでうまくいきます。

+0

強制的にアンインストーしましたが、ネットワーク操作の非同期性により、ネットワーク接続が確立される前に 'getPiIn'を呼び出していることを確認してください。ネットワークが接続され、あなたのView Controllerにこの通知を購読させると、あなたのネットワークコードに 'Notification 'を投稿させることをお勧めします。 – Paulw11

+0

私はこれを無駄にしようとしました。また、ネットワークが接続され、エラーが発生したときにビューがそれをロードするまでビューがロードされないことにも言及する価値があります。 –

+0

あなたは 'nil'のものを強制アンラップしています。これは保証されたクラッシュです。条件付きアンラップに変更することから始めます。これはクラッシュを取り除き、なぜ値が 'nil'であるのかを特定する必要があります – Paulw11

答えて

0

あなたが理解したら、サーバーからデータを取得したいので、URLSession()メソッドを使用します。dataTask これはJavaの方法ですか?コードがどのように機能し、今立っているとして はあなたが取得したい場合は、通知がUNUserNotificationCenter がgetPiIn()が呼び出されるPaulw11、で指摘したように、迅速

+0

サーバはPythonサーバですので、私が現在使用している方法を使用しなければならないことを理解しています。 –

0

でユーザーとサーバーの通信するための正しい方法で使用し、inStream!nilの値を持っています呼び出されます。ネットワーククラスの先頭にstatic let shared = Network()を追加し、そのクラスのすべての関数をすべてのファイルに渡って

関連する問題