从 HealthKit 获取一组血糖记录
Get an array of Blood Glucose records from HealthKit
我正在学习一些关于使用 swift 的 HealthKit 教程,我正在学习的教程之一是如何从 HealthKit 中检索一些数据,例如体重、身高、年龄。本教程展示了如何为它们检索最近的记录,以下代码显示:
func readMostRecentSample(sampleType:HKSampleType , completion: ((HKSample!, NSError!) -> Void)!)
{
// 1. Build the Predicate
let past = NSDate.distantPast() as! NSDate
let now = NSDate()
let mostRecentPredicate = HKQuery.predicateForSamplesWithStartDate(past, endDate:now, options: .None)
// 2. Build the sort descriptor to return the samples in descending order
let sortDescriptor = NSSortDescriptor(key:HKSampleSortIdentifierStartDate, ascending: false)
// 3. we want to limit the number of samples returned by the query to just 1 (the most recent)
let limit = 1
// 4. Build samples query
let sampleQuery = HKSampleQuery(sampleType: sampleType, predicate: mostRecentPredicate, limit: limit, sortDescriptors: [sortDescriptor])
{ (sampleQuery, results, error ) -> Void in
if let queryError = error {
completion(nil,error)
return;
}
// Get the first sample
let mostRecentSample = results.first as? HKQuantitySample
// Execute the completion closure
if completion != nil {
completion(mostRecentSample,nil)
}
}
// 5. Execute the Query
self.healthKitStore.executeQuery(sampleQuery)
}
然后在其他class开发者传参获取需要的最近记录,下面代码展示了获取身高记录的方法:
func updateHeight()
{
// 1. Construct an HKSampleType for Height
let sampleType = HKSampleType.quantityTypeForIdentifier(HKQuantityTypeIdentifierHeight)
// 2. Call the method to read the most recent Height sample
self.healthManager?.readMostRecentSample(sampleType, completion: { (mostRecentHeight, error) -> Void in
if( error != nil )
{
println("Error reading height from HealthKit Store: \(error.localizedDescription)")
return;
}
var heightLocalizedString = self.kUnknownString;
self.height = mostRecentHeight as? HKQuantitySample;
// 3. Format the height to display it on the screen
if let meters = self.height?.quantity.doubleValueForUnit(HKUnit.meterUnit()) {
let heightFormatter = NSLengthFormatter()
heightFormatter.forPersonHeightUse = true;
heightLocalizedString = heightFormatter.stringFromMeters(meters);
}
// 4. Update UI. HealthKit use an internal queue. We make sure that we interact with the UI in the main thread
dispatch_async(dispatch_get_main_queue(), { () -> Void in
self.heightLabel.text = heightLocalizedString
self.updateBMI()
});
})
}
我创建了一个与第一个类似的方法,但几乎没有改动,因此我可以获得一个包含 10 个葡萄糖记录的数组:
func readAllGlucose(sampleType:HKSampleType , completion: (([HKSample!], NSError!) -> Void)!)
{
let now = NSDate()
let df = NSDateFormatter()
df.dateFormat = "yyyy-MM-dd"
let pastt = df.dateFromString("2015-05-18")
//let mostRecentPredicate = HKQuery.predicateForSamplesWithStartDate(past, endDate:now, options: .None)
let allreadings = HKQuery.predicateForSamplesWithStartDate(pastt, endDate: now, options: .None)
// 2. Build the sort descriptor to return the samples in descending order
let sortDescriptor = NSSortDescriptor(key:HKSampleSortIdentifierStartDate, ascending: false)
// 3. we want to limit the number of samples returned by the query to just 1 (the most recent)
let limit = 10
// 4. Build samples query
let sampleQuery = HKSampleQuery(sampleType: sampleType, predicate: allreadings, limit: limit, sortDescriptors: [sortDescriptor])
{ (sampleQuery, results, error ) -> Void in
if let queryError = error {
completion([nil],error)
return;
}
// Get the first sample
let allSamples = results as? [HKQuantitySample]
// Execute the completion closure
if completion != nil {
completion(allSamples!,nil)
}
}
// 5. Execute the Query
self.healthKitStore.executeQuery(sampleQuery)
}
然后我创建了另一个类似于 updateHeight() 方法的方法,但当然做了必要的更改:
func updateLastGlucoRecords()
{
// 1. Construct an HKSampleType for weight
let sampleType = HKSampleType.quantityTypeForIdentifier(HKQuantityTypeIdentifierBloodGlucose)
// 2. Call the method to read the most recent weight sample
self.healthManager?.readAllGlucose(sampleType, completion: {([allReadings], error) -> Void in
if (error != nil) {
println("Error reading glucose readings from HealthKit Store: \(error.localizedDescription)")
return;
}
var glucoseLocalizedString = self.kUnknownString;
self.glucose = allReadings as? [HKQuantitySample]
for reading in readings {
if let record = reading.quantity {
glucoseLocalizedString = record
}
dispatch_async(dispatch_get_main_queue(), { () -> Void in
self.glucoReadings.append("\(glucoseLocalizedString)")
})
}
})
self.healthManager?.readMostRecentSample(sampleType, completion: { (mostRecentWeight, error) -> Void in
if( error != nil )
{
println("Error reading weight from HealthKit Store: \(error.localizedDescription)")
return;
}
var weightLocalizedString = self.kUnknownString;
// 3. Format the weight to display it on the screen
self.weight = mostRecentWeight as? HKQuantitySample;
if let kilograms = self.weight?.quantity.doubleValueForUnit(HKUnit.gramUnitWithMetricPrefix(.Kilo)) {
let weightFormatter = NSMassFormatter()
weightFormatter.forPersonMassUse = true;
weightLocalizedString = weightFormatter.stringFromKilograms(kilograms)
}
// 4. Update UI in the main thread
dispatch_async(dispatch_get_main_queue(), { () -> Void in
self.weightLabel.text = weightLocalizedString
self.updateBMI()
});
});
}
但不幸的是,我在行中遇到了两个错误:
self.healthManager?.readAllGlucose(sampleType, completion: {([allReadings], error) -> Void in
第一个错误:
[HKSample!]' is not a subtype of '<>
第二个错误:
Use of undeclared type 'allReadings'
如果有人有任何想法可以解决这个问题,我将不胜感激
提前致谢
我认为问题在于您在 ([allReadings], error)
中使用 allReadings
周围的方括号。尝试删除它们。您不需要指明 allReadings 是一个数组。这将由编译器推断,因为闭包的第一个参数是一个数组。
我正在学习一些关于使用 swift 的 HealthKit 教程,我正在学习的教程之一是如何从 HealthKit 中检索一些数据,例如体重、身高、年龄。本教程展示了如何为它们检索最近的记录,以下代码显示:
func readMostRecentSample(sampleType:HKSampleType , completion: ((HKSample!, NSError!) -> Void)!)
{
// 1. Build the Predicate
let past = NSDate.distantPast() as! NSDate
let now = NSDate()
let mostRecentPredicate = HKQuery.predicateForSamplesWithStartDate(past, endDate:now, options: .None)
// 2. Build the sort descriptor to return the samples in descending order
let sortDescriptor = NSSortDescriptor(key:HKSampleSortIdentifierStartDate, ascending: false)
// 3. we want to limit the number of samples returned by the query to just 1 (the most recent)
let limit = 1
// 4. Build samples query
let sampleQuery = HKSampleQuery(sampleType: sampleType, predicate: mostRecentPredicate, limit: limit, sortDescriptors: [sortDescriptor])
{ (sampleQuery, results, error ) -> Void in
if let queryError = error {
completion(nil,error)
return;
}
// Get the first sample
let mostRecentSample = results.first as? HKQuantitySample
// Execute the completion closure
if completion != nil {
completion(mostRecentSample,nil)
}
}
// 5. Execute the Query
self.healthKitStore.executeQuery(sampleQuery)
}
然后在其他class开发者传参获取需要的最近记录,下面代码展示了获取身高记录的方法:
func updateHeight()
{
// 1. Construct an HKSampleType for Height
let sampleType = HKSampleType.quantityTypeForIdentifier(HKQuantityTypeIdentifierHeight)
// 2. Call the method to read the most recent Height sample
self.healthManager?.readMostRecentSample(sampleType, completion: { (mostRecentHeight, error) -> Void in
if( error != nil )
{
println("Error reading height from HealthKit Store: \(error.localizedDescription)")
return;
}
var heightLocalizedString = self.kUnknownString;
self.height = mostRecentHeight as? HKQuantitySample;
// 3. Format the height to display it on the screen
if let meters = self.height?.quantity.doubleValueForUnit(HKUnit.meterUnit()) {
let heightFormatter = NSLengthFormatter()
heightFormatter.forPersonHeightUse = true;
heightLocalizedString = heightFormatter.stringFromMeters(meters);
}
// 4. Update UI. HealthKit use an internal queue. We make sure that we interact with the UI in the main thread
dispatch_async(dispatch_get_main_queue(), { () -> Void in
self.heightLabel.text = heightLocalizedString
self.updateBMI()
});
})
}
我创建了一个与第一个类似的方法,但几乎没有改动,因此我可以获得一个包含 10 个葡萄糖记录的数组:
func readAllGlucose(sampleType:HKSampleType , completion: (([HKSample!], NSError!) -> Void)!)
{
let now = NSDate()
let df = NSDateFormatter()
df.dateFormat = "yyyy-MM-dd"
let pastt = df.dateFromString("2015-05-18")
//let mostRecentPredicate = HKQuery.predicateForSamplesWithStartDate(past, endDate:now, options: .None)
let allreadings = HKQuery.predicateForSamplesWithStartDate(pastt, endDate: now, options: .None)
// 2. Build the sort descriptor to return the samples in descending order
let sortDescriptor = NSSortDescriptor(key:HKSampleSortIdentifierStartDate, ascending: false)
// 3. we want to limit the number of samples returned by the query to just 1 (the most recent)
let limit = 10
// 4. Build samples query
let sampleQuery = HKSampleQuery(sampleType: sampleType, predicate: allreadings, limit: limit, sortDescriptors: [sortDescriptor])
{ (sampleQuery, results, error ) -> Void in
if let queryError = error {
completion([nil],error)
return;
}
// Get the first sample
let allSamples = results as? [HKQuantitySample]
// Execute the completion closure
if completion != nil {
completion(allSamples!,nil)
}
}
// 5. Execute the Query
self.healthKitStore.executeQuery(sampleQuery)
}
然后我创建了另一个类似于 updateHeight() 方法的方法,但当然做了必要的更改:
func updateLastGlucoRecords()
{
// 1. Construct an HKSampleType for weight
let sampleType = HKSampleType.quantityTypeForIdentifier(HKQuantityTypeIdentifierBloodGlucose)
// 2. Call the method to read the most recent weight sample
self.healthManager?.readAllGlucose(sampleType, completion: {([allReadings], error) -> Void in
if (error != nil) {
println("Error reading glucose readings from HealthKit Store: \(error.localizedDescription)")
return;
}
var glucoseLocalizedString = self.kUnknownString;
self.glucose = allReadings as? [HKQuantitySample]
for reading in readings {
if let record = reading.quantity {
glucoseLocalizedString = record
}
dispatch_async(dispatch_get_main_queue(), { () -> Void in
self.glucoReadings.append("\(glucoseLocalizedString)")
})
}
})
self.healthManager?.readMostRecentSample(sampleType, completion: { (mostRecentWeight, error) -> Void in
if( error != nil )
{
println("Error reading weight from HealthKit Store: \(error.localizedDescription)")
return;
}
var weightLocalizedString = self.kUnknownString;
// 3. Format the weight to display it on the screen
self.weight = mostRecentWeight as? HKQuantitySample;
if let kilograms = self.weight?.quantity.doubleValueForUnit(HKUnit.gramUnitWithMetricPrefix(.Kilo)) {
let weightFormatter = NSMassFormatter()
weightFormatter.forPersonMassUse = true;
weightLocalizedString = weightFormatter.stringFromKilograms(kilograms)
}
// 4. Update UI in the main thread
dispatch_async(dispatch_get_main_queue(), { () -> Void in
self.weightLabel.text = weightLocalizedString
self.updateBMI()
});
});
}
但不幸的是,我在行中遇到了两个错误:
self.healthManager?.readAllGlucose(sampleType, completion: {([allReadings], error) -> Void in
第一个错误:
[HKSample!]' is not a subtype of '<>
第二个错误:
Use of undeclared type 'allReadings'
如果有人有任何想法可以解决这个问题,我将不胜感激
提前致谢
我认为问题在于您在 ([allReadings], error)
中使用 allReadings
周围的方括号。尝试删除它们。您不需要指明 allReadings 是一个数组。这将由编译器推断,因为闭包的第一个参数是一个数组。