我正在研究一个名为top10的数据框,并希望了解从2014年到2017年的下降百分比:
减少百分比的公式为import 'package:boxview_mobile_flutter/components/charts/date_from_millis_render_spec.dart';
import 'package:boxview_mobile_flutter/services/shared_prefs.dart';
import 'package:boxview_swagger_api/api.dart';
import 'package:boxview_charts_common/common.dart';
import 'package:flutter/material.dart';
import 'package:boxview_charts_flutter/flutter.dart' as charts;
import 'package:boxview_mobile_flutter/components/charts/chart_colors.dart';
class OverviewChart extends StatefulWidget {
final BedsidePatient patient;
final VitalsApi vitalsApi;
const OverviewChart({Key key, this.vitalsApi, this.patient}) : super(key: key);
@override
State<StatefulWidget> createState() {
return OverviewChartState();
}
}
const int _oneHour = 1000 * 60 * 60;
class PHRTime {
final int hour;
final int value;
final DateTime date;
PHRTime(this.value, this.date, this.hour);
}
class OverviewChartState extends State<OverviewChart> {
int highestHeartRate = 140;
int lowestHeartRate = 0;
List<PHRTime> highHR = [];
List<PHRTime> lowHR = [];
_fetchHeartRates() async {
VitalsSearchRequest req = VitalsSearchRequest();
req.organizationId = await SharedPreferencesHelper.getCurrentOrganizationID();
req.patientVisitId = widget.patient.currentVisitId;
int now = DateTime.now().toUtc().millisecondsSinceEpoch;
int start = now = (1000 * 60 * 60 * 24);
req.startTime = start;
req.stopTime = now;
widget.vitalsApi.searchHighLowsV1(vitalsSearchRequest: req).then((list) {
setState(() {
highHR.clear();
lowHR.clear();
if (list.isNotEmpty) {
list.sort((a, b) {
return b.highHeartRate - a.highHeartRate;
});
this.highestHeartRate = list[0].highHeartRate > 140 ? (list[0].highHeartRate / 20 + 2).toInt() * 20 : 140;
list.sort((a, b) {
return a.lowHeartRate - b.lowHeartRate;
});
this.lowestHeartRate = (list[0].lowHeartRate * 0.8).toInt();
list.forEach((p) {
if (p.highHeartRate > 0) {
highHR.add(PHRTime(p.highHeartRate,
DateTime.fromMillisecondsSinceEpoch(_normalize(p.highHeartRateTime), isUtc: true), p.hour));
}
});
list.forEach((p) {
if (p.lowHeartRate > 0) {
lowHR.add(PHRTime(p.lowHeartRate,
DateTime.fromMillisecondsSinceEpoch(_normalize(p.lowHeartRateTime), isUtc: true), p.hour));
}
});
}
});
});
}
int _normalize(int millis) {
return millis - (millis % _oneHour);
}
List<charts.Series<PHRTime, num>> _getOverviewScatterSeries() {
final Map<int, PHRTime> lowHRMap = {};
this.lowHR.forEach((p) {
lowHRMap.putIfAbsent(p.date.toLocal().millisecondsSinceEpoch, () => p);
});
return [
new charts.Series(id: 'HeartRates',
data: highHR,
colorFn: (_, __) => ChartColors.green,
domainFn: (PHRTime phr, _) => phr.date.toLocal().millisecondsSinceEpoch,
measureFn: (PHRTime phr, _) => phr.value,
radiusPxFn: (PHRTime phr, _) => 5.0,
labelAccessorFn: (PHRTime phr, _) => '${phr.value}',
domainLowerBoundFn: (PHRTime phr, _) => phr.date.toLocal().millisecondsSinceEpoch,
domainUpperBoundFn: (PHRTime phr, _) => phr.date.toLocal().millisecondsSinceEpoch,
measureLowerBoundFn: (PHRTime phr, _) => lowHRMap[phr.date.toLocal().millisecondsSinceEpoch]?.value ?? phr.value,
measureUpperBoundFn: (PHRTime phr, _) => phr.value,
),
];
}
@override
Widget build(BuildContext context) {
return _buildScatterChart(context);
}
Widget _buildScatterChart(BuildContext context) {
final num now = _normalize(DateTime.now().toLocal().millisecondsSinceEpoch) * 1.0;
final num start = now - (_oneHour * 24.0);
return new charts.ScatterPlotChart(_getOverviewScatterSeries(),
animate: true,
primaryMeasureAxis: new charts.NumericAxisSpec(
tickProviderSpec:
new charts.BasicNumericTickProviderSpec(zeroBound: false)),
domainAxis: new charts.NumericAxisSpec(
viewport: charts.NumericExtents(start - _oneHour, now + _oneHour),
tickProviderSpec:
new charts.BasicNumericTickProviderSpec(zeroBound: false, dataIsInWholeNumbers: true),
renderSpec: DateFromMillisRenderSpec(),
),
defaultRenderer:
new charts.PointRendererConfig(pointRendererDecorators: [
new charts.ComparisonPointsDecorator(
symbolRenderer: new charts.CylinderSymbolRenderer())
])
);
}
@override
void initState() {
super.initState();
_fetchHeartRates();
}
}
原始df(top10):
Difference/Total2014 * 100
输入
Zip Total2014 Total2017 Difference
1 ZCT 44108 25122 22048 3074
2 ZCTA5 43607 23547 21560 1987
3 ZCTA5 44104 22479 20541 1938
两种情况下的Repex输出:
top10 <- mutate(top10,decrease = (Difference/Total2014)*100)
top10 <- mutate(top10,decreasepc = decrease*100)
如您所见,减少百分比仍显示为1.22,而不是12.2%。另外,如何在mutate中将小数点后两位取整?
答案 0 :(得分:0)
百分比是一种格式化数字的方式。例如,您可以使用scales
:
library(dplyr)
top10 <- mutate(top10, decrease = (Difference/Total2014))
top10 <- mutate(top10, decreasepct = scales::percent(decrease))
> top10
ID Zip Total2014 Total2017 Difference decrease decreasepct
1 ZCT 44108 25122 22048 3074 0.12236287 12.24%
2 ZCTA5 43607 23547 21560 1987 0.08438442 8.44%
3 ZCTA5 44104 22479 20541 1938 0.08621380 8.62%
请注意,尽管将数字格式化为百分比会将列转换为字符:
> class(top10$decreasepc)
[1] "character"
top10 <- read.table(text = "
ID Zip Total2014 Total2017 Difference
ZCT 44108 25122 22048 3074
ZCTA5 43607 23547 21560 1987
ZCTA5 44104 22479 20541 1938", head = TRUE)