NSMassFormatter does not return localized values - ios

I want to use iOS 8's new HealthKit NSFormatters to show the weight of a person according to locale. So 80 kgs in Europe should be formatted as 176.36 pounds in the US, but 80 kg in Europe.
For this I use the unitStringFromKilograms method, which according to the Docs should return:
A localized string representing the unit. This method selects the correct unit based on the formatter’s locale, the magnitude of the value, and the forPersonMassUse property.
However, the following piece of code, on several laptops with multiple locales and iOS devices with metric locales, always return 'pounds'.
Is this a bug or did I forget something so obvious that Apple didn't mention it in their docs?
import HealthKit
let massFormatter = NSMassFormatter()
massFormatter.forPersonMassUse = true // it doesn't matter if this is false
massFormatter.unitStyle = .Long
var massFormatterUnit = NSMassFormatterUnit.Kilogram
// This unitString SHOULD be according to locale, e.g. kg in Europe, pounds in us.
// instead it always returns 'pounds'
let unitString = massFormatter.unitStringFromKilograms(80, usedUnit: &massFormatterUnit)

Related

When could the user's Locale.current.region be nil?

The locale region is optional from Foundation. It is my understanding that this property is read from the device under iOS Settings > General > Language & Region > Region.
What is the possible scenarios that the region property is nil; why is it optional?
It is my understanding that this property is read from the device under iOS Settings > General > Language & Region > Region
Well, that would be Locale.current, but that is not the only instance of Locale instance there can be. You can create your own locales.
More accurately, region is:
This property corresponds to the rg key of the Unicode BCP 47 extension.
For locale instances created with the rg specifier (such as en-GB#rg=US), or with a custom Locale.Components, this property represents the custom region. Otherwise, it represents the language’s region.
I tried setting Locale.Components.region to nil, but the Locale created this way still has the default region of the language:
var components = Locale.Components(languageCode: .english)
components.region = nil
let locale = Locale(components: components)
print(locale.region) // US
If the Locale.Language does not belong to any region though, then region would be nil. And such Locale.Languages do exist! For example:
// zxx - no linguistic content
let unidentified = Locale(languageCode: .unidentified)
print(unidentified.region) // nil
// mul - multiple languages
let multiple = Locale(languageCode: .multiple)
print(multiple.region) // nil
So region has to be optional at least because of the mul and zxx "languages", as required in BCP 47.

intl's NumberFormat is giving 922,337,203,685,477,580,700 on very huge number

I am using intl's NumberFormat class to format my numbers.
my pubspec.yaml is something like this:
intl:
I have this very huge number when a user type on the textfield:
1,000,000,000,000,000,000,000
Without using intl, the output is this:
1e+21
And I wanted to format it so it could be readable by a normal human being.
So I did something like this:
NumberFormat myFormat = new NumberFormat("#,##0.00", "en_US");
...
String _input = _textController.text; // user's input
double _number = double.tryParse(_input);
String _formatted = '${myFormat.format(_number)}';
This worked on numbers lesser than 1e+21. However, when the user's input is equal to or greater than 1e+21, it gives a value of:
922,337,203,685,477,580,700.00 // output of 1e+21
922,337,203,685,477,580,700,000,000,000.00 // output of 1e+30
I am completely clueless why it gave a number like that.
I would appreciate any form of help.
You can use this flutter package bignum.

HL7 Encoding/Separator Characters

In regards to HL7 pipe-delimited data, how exactly do the encoding characters (|^~\&) work?
Is the following example of fields, field repetitions, components and their sub-components correct when parsing raw HL7 data?
PID|1||||||||||||1234567890^somedata&moredata^TESTEMAIL#GMAIL.COM~0987654321
Field (|):
PID13 = 1234567890^somedata&moredata^TESTEMAIL#GMAIL.COM~0987654321
Field repetition (~):
PID13~1 = 1234567890^somedata&moredata^TESTEMAIL#GMAIL.COM
PID13~2 = 0987654321
Component (^):
PID13.1 = 1234567890
PID13.2 = somedata&moredata
PID13.3 = TESTEMAIL#GMAIL.COM
Sub-component (&):
PID13.2.1 = somedata
PID13.2.2 = moredata
PID13.3.1 = TESTEMAIL#GMAIL.COM
PID13.3.2 =
Without understanding the left-hand side structure you're trying to assign stuff to, it's impossible to tell you if you're doing it right.
There is however one right way to parse the segment/field in question.
Here's a link to the specs I reference here
From section 2.5.3 of the HL7v2.7 Standard:
Each field is assigned a data type that defines the value domain of the field – the possible values that it may
take.
If you pull up section 3.4.2.13 (PID-13) you'll see a breakdown of each component and subcomponent. Technically, the meaning of subcomponents and components can vary by field, but mostly they just vary by data type.
In your example, you don't treat the repetitions as separate instances of XTN data types. I would re-write using array syntax as so:
Field repetition (~):
PID13[0] = 1234567890^somedata&moredata^TESTEMAIL#GMAIL.COM
PID13[1] = 0987654321
Component (^):
PID13[0].1 = 1234567890
PID13[0].2 = somedata&moredata
PID13[0].3 = TESTEMAIL#GMAIL.COM
Sub-component (&):
PID13[0].2.1 = somedata
PID13[0].2.2 = moredata
The psuedo-code in the same specification section 2.6.1 may be helpful as well
foreach occurrence in ( occurrences_of( field ) ) {
construct_occurrence( occurrence );
if not last ( populated occurrence ) insert repetition_separator;
/* e.g., ~ */
}
It's important to remember that those different subcomponents have different meaning because PID-13 is a XTN type.
PID-13 is a problematic example because historically, the order of PID-13 mattered. The first repetition was "primary". Over time the field has also become the landing place for e-mail addresses, pager numbers, etc. So good luck trying to make sense out of real-world data.

How to convert "42°33'N, 1°33'E" to "42.55|1.55" in Scribunto (MediaWiki-hosted Lua)

Scribunto is a MediaWiki-hosted version of Lua.
I believe it is fairly standard Lua.
I want to convert geographic coordinates from this format:
42°33'N, 1°33'E
... to this format:
42.55|1.55
How to do this in Scribunto?
This assumes the input string is strictly of the form in the post. If there's any variability e.g. it can omit the minutes, include seconds, latitude and longitude can be separated differently, or whatever, the pattern will need to change.
function translate_coords(str)
assert(type(str)=="string")
local patt = "(%d+)°(%d+)'([NS]), (%d+)°(%d+)'([WE])"
local latd,latm,latdir,lngd,lngm,lngdir = string.match(str,patt)
assert(latd and latm and latdir)
assert(lngd and lngm and lngdir)
latd = latdir=="S" and -latd or latd
lngd = lngdir=="W" and -lngd or lngd
return ""..(latd+latm/60).."|"..(lngd+lngm/60)
end

Date Formatting in actionscript

I have the following problem: I take a date (as a string data type) from the user. Now, I want to know if there is a a function in actionscript that will convert it to a date format. Right now, I am just parsing the string and concatenating the pieces back together. Ie:
changeDateString = date.getFullYear().toString() + '/' + (date.getMonth()+1).toString() + '/' + date.getDate();
But for months like May, it will return "5" and not "05". I have similar problems for days like "9" or "7." Is there something in the library that will do this for me? (For the moment, I can go ahead and manually concatenate the "0" in front, but this seems like a hassle to do.)
I know this is a simple question, but I a novice.
Thanks.
Use a date formatter for that:
http://help.adobe.com/en_US/FlashPlatform/beta/reference/actionscript/3/mx/formatters/DateFormatter.html
You configure your formatter to use the format based on the types listed and use it to output your date.
var formatter:DateFormatter = new DateFormatter();
formatter.formatString = "m/d/Y";
var example:Date = new Date(2010, 0, 5, 10, 25);
trace(formatter.format(example)); // Displays: 01/05/2010
Just use the Pattern Letter/Description grid in the docs to find the right format for your needs.

Resources