Swift 4 - структурировать статические переменные, не отображая значения - PullRequest
0 голосов
/ 04 июля 2018

Я новичок в стремительности, но учусь на ходу. У меня есть функция для получения данных из таблицы AWS DynamoDB, используя for..loop. Я собираю значения полей элементов таблицы в структурных переменных в цикле, но когда я вызываю структурные переменные в табличном представлении, он показывает пустой массив как [] на экране журнала в Xcode. Вот код:


import Foundation
import SQLite3
import UIKit
import AWSDynamoDB

struct MyVariables {
    static var empDict: [String: String] = [:]
    static var arrayEmployees = Array<Dictionary<String, String>>()
}

// This is a class defined to hold various methods to be used throughout the app.
class DatabaseClass: UIViewController, UITextFieldDelegate
{
    // other methods within DatabaseClass
    // ........
    //
    //
    // Scan DynamoDB table for employees
    func scanEmployees () {
        let dynamoDBObjectMapper = AWSDynamoDBObjectMapper.default()
        let scanExpression = AWSDynamoDBScanExpression()
        scanExpression.limit = 20

        dynamoDBObjectMapper.scan(Employees.self, expression: scanExpression).continueWith(block: { (task:AWSTask<AWSDynamoDBPaginatedOutput>!) -> Any? in
            if let error = task.error as NSError? {
                print("The request failed. Error: \(error)")
            }

            let paginatedOutput = task.result!

            for emp in paginatedOutput.items as! [Employees]  {
                if emp._empid != nil {
                    MyVariables.empDict["Empid"] = emp._empid
                } else {
                    MyVariables.empDict["Empid"] = nil
                }

                if emp._email != nil {
                    MyVariables.empDict["email"] = emp._email
                } else {
                    MyVariables.empDict["email"] = nil
                }

                if emp._firstname != nil {
                    MyVariables.empDict["firstname"] = emp._firstname
                } else {
                    MyVariables.empDict["firstname"] = nil
                }

                if emp._lastname != nil {
                    MyVariables.empDict["lastname"] = emp._lastname
                } else {
                    MyVariables.empDict["lastname"] = nil
                }

                if emp._location != nil {
                    MyVariables.empDict["location"] = emp._location
                } else {
                    MyVariables.empDict["location"] = nil
                }

                if emp._mobile != nil {
                    MyVariables.empDict["mobile"] = emp._mobile
                } else {
                    MyVariables.empDict["mobile"] = nil
                }

                if emp._work != nil {
                    MyVariables.empDict["work"] = emp._work
                } else {
                    MyVariables.empDict["work"] = nil
                }

                if emp._site != nil {
                    MyVariables.empDict["site"] = emp._site
                } else {
                    MyVariables.empDict["site"] = nil
                }

                MyVariables.arrayEmployees.append(MyVariables.empDict)
                //print(MyVariables.arrayEmployees)
            } // for loop

            print ("printing array employees just after for loop")
            print(MyVariables.arrayEmployees)
            // The above print works

            return nil
        })

        // print(MyVariables.arrayEmployees)
        // Above doesn’t print
    }
}

Позже я вызываю этот DatabaseClass в виде таблицы следующим образом:

class JsonParseViewController: UIViewController {
    override func viewDidLoad() {
        super.viewDidLoad()

        let createEmp = DatabaseClass()
        createEmp.scanEmployees()
        print("in JsonParseViewController, calling scan function")
        print(MyVariables.arrayEmployees)

При запуске в симуляторе в файле журнала отображается следующее:

in JsonParseViewController, calling scan function
[]
printing array employees just after for loop
[["location": "XXXXXX", "email": "johnSmith1@email.com", "firstname": "John1", "lastname": "Smith1", "mobile": "123-456-7890", "work": "123-456-7890", "Empid": "12345", "site": "KKKKKK"], ["location": "YYYYY", "email": "johnSmith8@email.com", "firstname": "John8", "lastname": "Smith8", "mobile": "123-456-7890", "work": "123-456-7890", "Empid": "12415", "site": "ZZZZZ"], ......etc]]

При выполнении функции scanEmployees кажется, что она пропускает команду сканирования DynamoDB и возвращает [] в виде таблицы, но каким-то образом переходит к функции и выполняет данные. Не удается захватить данные в структурных переменных. Я пытался исправить это в течение многих дней.

Ответы [ 2 ]

0 голосов
/ 04 июля 2018

У вас проблема со статической памятью. Я бы предложил не использовать статические значения, это очень плохая практика. Решением может быть создание структуры внутри класса DatabaseClass. Например, var myVariables = MyVariables () и заполните его таким же образом. Теперь у вас есть возможность вернуть его или использовать из объекта DatabaseClass. Сейчас я покажу пример, как это должно выглядеть.

struct MyVariables {
    var empDict: [String: String] = [:]
    var arrayEmployees = Array<Dictionary<String, String>>()
}

// This is a class defined to hold various methods to be used throughout the app.
class DatabaseClass: UIViewController, UITextFieldDelegate
{
    // other methods within DatabaseClass
    // ........
    //
    //
    // Scan DynamoDB table for employees
  public var myVariables = MyVariables()

 func scanEmployees () {
        let dynamoDBObjectMapper = AWSDynamoDBObjectMapper.default()
        let scanExpression = AWSDynamoDBScanExpression()
        scanExpression.limit = 20

        dynamoDBObjectMapper.scan(Employees.self, expression: scanExpression).continueWith(block: { (task:AWSTask<AWSDynamoDBPaginatedOutput>!) -> Any? in
            if let error = task.error as NSError? {
                print("The request failed. Error: \(error)")
            }

            let paginatedOutput = task.result!

            for emp in paginatedOutput.items as! [Employees]  {
                myVariables.empDict["Empid"] = emp._empid
                myVariables.empDict["email"] = emp._email
                myVariables.empDict["firstname"] = emp._firstname
                myVariables.empDict["lastname"] = emp._lastname
                myVariables.empDict["location"] = emp._location
                myVariables.empDict["mobile"] = emp._mobile
                myVariables.empDict["work"] = emp._work
                myVariables.empDict["site"] = emp._site

                myVariables.arrayEmployees.append(myVariables.empDict)
                //print(myVariables.arrayEmployees)
            } // for loop

            print ("printing array employees just after for loop")
            print(myVariables.arrayEmployees)
            // The above print works

            return nil
        })

        // print(myVariables.arrayEmployees)
        // Above doesn’t print
    }
}

//then use it in this way


    class JsonParseViewController: UIViewController {
        override func viewDidLoad() {
            super.viewDidLoad()

            let createEmp = DatabaseClass()
            createEmp.scanEmployees()
            print("in JsonParseViewController, calling scan function")
            print(createEmp.myVariables.arrayEmployees)

         }
      }
0 голосов
/ 04 июля 2018

Вы пропускаете асинхронный вызов

func scanEmployees (completion:@escaping ()-> Void) {

    let dynamoDBObjectMapper = AWSDynamoDBObjectMapper.default()
    let scanExpression = AWSDynamoDBScanExpression()
    scanExpression.limit = 20

    dynamoDBObjectMapper.scan(Employees.self, expression: scanExpression).continueWith(block: { (task:AWSTask<AWSDynamoDBPaginatedOutput>!) -> Any? in

        if let error = task.error as NSError? {
            print("The request failed. Error: \(error)")
        }

        let paginatedOutput = task.result! 

            for emp in paginatedOutput.items as! [Employees]  {

                myVariables.empDict["Empid"] = emp._empid
                myVariables.empDict["email"] = emp._email
                myVariables.empDict["firstname"] = emp._firstname
                myVariables.empDict["lastname"] = emp._lastname
                myVariables.empDict["location"] = emp._location
                myVariables.empDict["mobile"] = emp._mobile
                myVariables.empDict["work"] = emp._work
                myVariables.empDict["site"] = emp._site

                MyVariables.arrayEmployees.append(MyVariables.empDict)
                //print(MyVariables.arrayEmployees)

            } // for loop
                print ("printing array employees just after for loop")
                print(MyVariables.arrayEmployees)
              // The above print works

             completion()
             return nil
   } 
 ) 

   // print(MyVariables.arrayEmployees)
   // Above doesn’t print
} 

//

при звонке

createEmp.scanEmployees {

       print(MyVariables.arrayEmployees)
}

Примечание: Я рекомендую использовать SwiftyJson или JSONDecoder вместо ручного анализа ключей

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...