Swift 4 Firebase Realtime Database nested dictionary - swift

ZERO experience, so bear with me...
Im trying to retrieve data from a Firebase Realtime Database and im using this code..
func fetchData(){
refHandle = ref?.child("caddata").observe(.childAdded, with: { (snapshot) in
if let values = snapshot.value as? [AnyHashable: Any] {
for value in values.values {
print (value)
"values" shows the following:
▿ 1 element
▿ 0 : 2 elements
▿ key : AnyHashable("parsedContent")
- value : "parsedContent"
▿ value : 1 element
▿ 0 : 7 elements
▿ 0 : 2 elements
- key : location
- value : 1234 ANY ADDRESS ST ANYTOWN
▿ 1 : 2 elements
- key : agencyId
- value : 3-08
▿ 2 : 2 elements
- key : alarmLevel
- value : 0
▿ 3 : 2 elements
- key : agencyEventSubtypeCode
- value : 59-C-3O
▿ 4 : 2 elements
- key : originatingAction
- value : CadEventNew
▿ 5 : 2 elements
- key : agencyEventId
- value : CC17187712
▿ 6 : 2 elements
- key : dateTime
- value : 2017-12-22T22:37:27Z
Which I believe you'd refer to as a nested dictionary. "value" prints:
▿ 1 element
▿ 0 : 7 elements
▿ 0 : 2 elements
- key : location
- value : 1234 ANY ADDRESS ST ANYTOWN
▿ 1 : 2 elements
- key : agencyId
- value : 3-08
▿ 2 : 2 elements
- key : alarmLevel
- value : 0
▿ 3 : 2 elements
- key : agencyEventSubtypeCode
- value : 59-C-3O
▿ 4 : 2 elements
- key : originatingAction
- value : CadEventNew
▿ 5 : 2 elements
- key : agencyEventId
- value : CC17187712
▿ 6 : 2 elements
- key : dateTime
- value : 2017-12-22T22:37:27Z
I have no idea how to get into the next level or levels to retrieve the value for each key shown. The end goal is to show some or all of the data in a tableview. Like I said, I have no experience. Any help (in the simplest terms) would be greatly appreciated.

Looks like your value is another dictionary. So
if let dict = value as Dictionary {
for key in dict.allKeys {
print("the value for key \(key) is:")
print(dict[key])
}
}

Related

Swift Data.subdata fails with EXC_BAD_INSTRUCTION (code=EXC_I386_INVOP, subcode=0x0)

I am attempting to retrieve a subset of data from a Data object. When I attempt to get the data using subdata(in:) I get the mentioned error. I cannot figure out what I am doing wrong as all values appear correct. The code in question is:
let tempData = incomingDataBuffer.subdata(in: 0..<headerSizeInBytes)
using the lldb i've investigated and found that everything looks correct.
(lldb) po incomingDataBuffer.count
8
(lldb) po headerSizeInBytes
6
(lldb) po incomingDataBuffer
▿ 8 bytes
- count : 8
▿ pointer : 0x0000600000002a42
- pointerValue : 105553116277314
▿ bytes : 8 elements
- 0 : 17
- 1 : 6
- 2 : 29
- 3 : 49
- 4 : 2
- 5 : 0
- 6 : 1
- 7 : 6
(lldb) po incomingDataBuffer.subdata(in: 0..<headerSizeInBytes)
error: Execution was interrupted, reason: EXC_BAD_INSTRUCTION (code=EXC_I386_INVOP, subcode=0x0).
The process has been returned to the state before expression evaluation.
This Doesn't make any sense to me. All the values appear correct. Nothing is nil. Why would I get this failure? Thanks for help. :)
The indices of a Data value (or of collections in general) are not necessarily zero-based. A slice shares the indices with the originating data. Example:
let buffer = Data(bytes: [1, 2, 3, 4, 5, 6])[2..<4]
print(buffer.count) // 2
print(buffer.indices) // 2..<4
let tmpData = buffer.subdata(in: 0..<2)
// 💣 Thread 1: EXC_BAD_INSTRUCTION (code=EXC_I386_INVOP, subcode=0x0)
Therefore you have to take the start index into account:
let tmpData = buffer[buffer.startIndex ..< buffer.startIndex + 2]
print(tmpData as NSData) // <0304>
or simply use the prefix:
let tmpData = buffer.prefix(2)
print(tmpData as NSData) // <0304>
Applied to your case:
let tempData = incomingDataBuffer.prefix(headerSizeInBytes)

Swift 3 Array pagination?

Hello I'm trying to do pagination for array of contacts, some how i the code crashed on paged 2
here is my code :
// Initialize
let limit : Int = 10
var page : Int = self.defaults.integer(forKey: "ConPage") == 0 ? 1 : self.defaults.integer(forKey: "ConPage")
var start : Int = page == 0 || page == 1 ? 0 : limit * ( page-1)
var increment : Int = 1
var data = (contacts)?[start...limit]
print("[CONTACTS SYNC][LoadUpContacts] Success \(success) , Data : \(data?.count) , start : \(start) , Limit : \(limit) , Page : \(page), Total : \(contacts?.count) ")
for contact in data!
{
print("\(increment) : \(contact.name) ")
increment = increment + 1
}
//go Next
self.defaults.set(page+1, forKey: "ConPage")
self.LoadUpContacts()
and here is the crash log :
fatal error: Can't form Range with upperBound < lowerBound
2017-07-10 11:32:01.758790+0300 muzeit[6085:2216770] fatal error: Can't form Range with upperBound < lowerBound
What is the best way to paginate an array in swift 3 ?
the problem was in array range , so i fixed it and i hope it solve someone else issue , below is the correct code for array pagination in Swift 3
let total : Int = (contacts?.count)!
let limit : Int = 20
let page : Int = self.defaults.integer(forKey: "ConPage") == 0 ? 1 : self.defaults.integer(forKey: "ConPage")
let start : Int = page == 0 || page == 1 ? 0 : (limit * page) - limit
var end : Int = start + limit
end = end >= total ? total : end
end = end - 1
let data = start >= total ? [] : (contacts)?[start...(end)]
To respond to your question in the comment. In fact, the subArrayWithRange is only available in Objective-c. So you can create a subarray from an index, with length by:
let arr = [1, 3, 4, 5, 10, 2, 100, 40, 1244, 23]
let startIndex = 3
let length = 4
let arr2 = arr[startIndex..<(startIndex + length)] //print [5, 10, 2, 100]
And to get the contents of a page from your items, you have to calculate the right startIndex and the endIndex of your subarray. Be attention that, the subcript returns a ArraySlice, not Array. You may to cast it to Array.
//page start from 0
func getPageItems(page: UInt, allItems: [Int], maxItemsPerPage: UInt) -> [Int] {
let startIndex = Int(page * maxItemsPerPage)
var length = max(0, allItems.count - startIndex)
length = min(Int(maxItemsPerPage), length)
guard length > 0 else { return [] }
return Array(allItems[startIndex..<(startIndex + length)])
}
the call:
let arr3 = getPageItems(page: 3, allItems: arr, maxItemsPerPage: 4)
will return [1244, 23]
Looking at the error it seems like there is an issue with the array range.
If you look at the line:
var data = (contacts)?[start...limit]
of your code, you can see that the limit is always equal to 10. And the range upper...lower represents the start and the end of the range. So you should properly calculate the lower bound also in the way you calculate the upper bound.

Swift 3 generic type function to clamp numeric values into 0 and 1 interval

I want to write a function that clamps a numeric value into the closed 0,1 interval:
func clamp01<T:???>(_ value:T) -> T {
return value < 0 ? 0 : value > 1 ? 1 : value
}
In Swift 3 if I use T:Strideable I get a complaint that 0 and 1 must be typecast (0 as! T resolves the issue, but it's a forced cast).
In Swift 4 I may be able to use T:Numeric but I haven't tried that -- I am looking for a solution in Swift 3.
You could define the function for all Comparable types which
are also ExpressibleByIntegerLiteral, that covers all integer
and floating point types:
func clamp01<T: Comparable & ExpressibleByIntegerLiteral>(_ value: T) -> T {
return value < 0 ? 0 : value > 1 ? 1 : value
}

[torch]how to read weights in nn model

I constructed the nn model using itorch notebook.
model = nn.Sequential()
model:add(nn.Reshape(ninputs))
model:add(nn.Linear(ninputs,noutputs))
Input data to the model
output = model:forward(input)
Then, I print the model and got this.
print(model)
nn.Sequential {
[input -> (1) -> (2) -> output]
(1): nn.Reshape(3072)
(2): nn.Linear(3072 -> 10)
}
{
gradInput : DoubleTensor - empty
modules :
{
1 :
nn.Reshape(3072)
{
_input : DoubleTensor - empty
nelement : 3072
train : true
output : DoubleTensor - size: 3072
gradInput : DoubleTensor - empty
size : LongStorage - size: 1
_gradOutput : DoubleTensor - empty
batchsize : LongStorage - size: 2
}
2 :
nn.Linear(3072 -> 10)
{
gradBias : DoubleTensor - size: 10
weight : DoubleTensor - size: 10x3072
train : true
bias : DoubleTensor - size: 10
gradInput : DoubleTensor - empty
gradWeight : DoubleTensor - size: 10x3072
output : DoubleTensor - size: 10
}
}
train : true
output : DoubleTensor - size: 10
}
how to read the weight in nn.linear ?
Thanks in advance.
Oh, it is similar to php
model.modules[2].weight
I find that model.modules[1].weight is similar to model:get(1).weight, but both can't get the parameters from the table layer like residual block. In this way the residual block as a layer.
however, we can use params, gradParams = model:parameters() to get the parameters for each layer even in the table layer.
It is worth noting that, in the second way, each layer of the network parameters are divided into two layers and arranged in layers

Leafletjs legand value = 0

I would like to know (if it's possible) how to add a 0 value ine Leafletjs block's legend.
For an example, this is my class :
function getColorPOPULATION(d) {
return d > 500 ? '#004590' :
d > 250 ? '#00ABFF' :
d > 1 ? '#A0E0FF' :
'#FFF4D0' ;
... and my grades (div legend) :
grades = [0, 1, 250, 500],
-> I get this result :
0 - 1
1 - 250
250 - 500
500+
I would like to isolate the 0 value (my first class will be 0). Does Leafletjs able to do this ?
Thank you,