我尝试了一个小代码,但我有一个无法解释的奇怪行为。
我想根据一个值返回基于键的映射的“键值”。
我的代码具有正值。
如果该值不在数组中,则返回 null。
仅当值包含在我的数组中时,它也适用于负值。
如果我输入一个低于我的数组的负值,那么它返回的不是空值而是零,这是错误的!
我的 map 中的键必须是字符串。
我可以在 dartPad 上测试的代码:
import 'dart:collection';
void main() {
int myVar = -360;
Map<String, dynamic> values = {
"-200" : 42,
"-100" : 21,
"0" : 0,
"100" : -22,
"150" : -30,
"200" : -43,
"300" : -64
};
Map<String, dynamic> filter(int myVar, Map<String, dynamic> values) {
SplayTreeMap<String, dynamic> newval = SplayTreeMap.of(values);
String convertString = myVar.toString();
if (values.containsKey(convertString)) {
return {convertString: values[convertString]};
}
String lowerKey;
String upperKey;
if(myVar > 0){
lowerKey = newval.lastKeyBefore(convertString);
upperKey = newval.firstKeyAfter(convertString);
}
else{
lowerKey = newval.firstKeyAfter(convertString);
upperKey = newval.lastKeyBefore(convertString);
}
print(lowerKey);
print(upperKey);
return {
if (lowerKey != null) lowerKey: values[lowerKey],
if (upperKey != null) upperKey: values[upperKey],
};
}
var result = filter(myVar, values);
print('============================');
print(result);
}
最佳答案
首先,我想对 dynamic
的使用提出一个小小的提示。在代码中。使用 dynamic
完全没问题在 JSON 解析等运行时无法确定类型的情况下。但是在这种情况下,可以确定所有类型并使用dynamic
没有必要。所以我修复了代码以删除 dynamic
的使用并删除了不必要的打字:
import 'dart:collection';
void main() {
const myVar = -360;
final values = {
"-200": 42,
"-100": 21,
"0": 0,
"100": -22,
"150": -30,
"200": -43,
"300": -64
};
Map<String, int> filter(int myVar, Map<String, int> values) {
final newVal = SplayTreeMap.of(values);
final convertString = myVar.toString();
if (values.containsKey(convertString)) {
return {convertString: values[convertString]};
}
String lowerKey;
String upperKey;
if (myVar > 0) {
lowerKey = newVal.lastKeyBefore(convertString);
upperKey = newVal.firstKeyAfter(convertString);
} else {
lowerKey = newVal.firstKeyAfter(convertString);
upperKey = newVal.lastKeyBefore(convertString);
}
print(lowerKey);
print(upperKey);
return {
if (lowerKey != null) lowerKey: values[lowerKey],
if (upperKey != null) upperKey: values[upperKey],
};
}
final result = filter(myVar, values);
print('============================');
print(result);
}
您的问题是您正在使用 SplayTreeMap
对 values
中的 key 进行排序但是您使用字符串来表示您的数字。这相当令人困惑,因为数字是有效的键。但这也意味着您在 SplayTreeMap
中的排序是字母而不是数字。这正是您的代码无法按预期工作的原因。您可以将 key 类型更改为
int
或提供 compare
方法到您的SplayTreeMap
这改变了排序的完成方式。我做了以下示例,其中我将键的类型更改为
int
这使您的代码工作:import 'dart:collection';
void main() {
const myVar = -360;
final values = {
-200: 42,
-100: 21,
0: 0,
100: -22,
150: -30,
200: -43,
300: -64
};
Map<int, int> filter(int myVar, Map<int, int> values) {
final newVal = SplayTreeMap.of(values);
if (values.containsKey(myVar)) {
return {myVar: values[myVar]};
}
int lowerKey;
int upperKey;
if (myVar > 0) {
lowerKey = newVal.lastKeyBefore(myVar);
upperKey = newVal.firstKeyAfter(myVar);
} else {
lowerKey = newVal.firstKeyAfter(myVar);
upperKey = newVal.lastKeyBefore(myVar);
}
print(lowerKey);
print(upperKey);
return {
if (lowerKey != null) lowerKey: values[lowerKey],
if (upperKey != null) upperKey: values[upperKey],
};
}
final result = filter(myVar, values);
print('============================');
print(result);
}
输出 -200
null
============================
{-200: 42}
关于Dart 为什么我的代码不适用于负值,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/62499714/