Поскольку вы сортируете лексически, попробуйте этот код:
#!/usr/bin/perl
use strict;
use warnings;
my $ref = [ 5.0e-5,4.2e-5,4.3e-5,4.4e-5,4.4e-5,4.2e-5,4.2e-5,4.0e-5];
print "Perl with cmp\n";
for my $val (sort @$ref) {
printf "%f \n", $val;
}
print "Perl with <=>\n";
for my $val (sort { $a <=> $b } @$ref) {
printf "%f \n", $val;
}
print "C\n";
test($ref);
use Inline C => <<'END_OF_C_CODE';
void test(SV* sv, ...) {
I32 i;
I32 arrayLen;
AV* data;
float retval;
SV** pvalue;
Inline_Stack_Vars;
data = SvUV(Inline_Stack_Item(0));
/* Determine the length of the array */
arrayLen = av_len(data);
// sort
sortsv(AvARRAY(data),av_len(data)+1,Perl_sv_cmp_locale);
arrayLen = av_len(data);
for (i = 0; i < arrayLen+1; i++) {
pvalue = av_fetch(data,i,0); /* fetch the scalar located at i .*/
retval = SvNV(*pvalue); /* dereference the scalar into a number. */
printf("%f \n",newSVnv(retval));
}
}
END_OF_C_CODE
Конечно, лексически 0.00040
меньше, чем 0.00042
, но вы не сравниваете 0.00040
с 0.00042
; вы сравниваете число 0.00040
, преобразованное в строку, с числом 0.00042
, преобразованным в строку. Когда число становится слишком большим или маленьким, строковая логика Perl прибегает к использованию научных обозначений. Итак, вы сортируете набор строк
"4.2e-05", "4.2e-05", "4.2e-05", "4.3e-05", "4.4e-05", "4.4e-05", "4e-05", "5e-05"
, которые правильно отсортированы. Perl радостно превращает эти строки в их числа, когда вы просите об этом в формате %f
в printf
. Вы можете сами упорядочить числа, но поскольку вы заявили, что хотите, чтобы это было быстрее, это было бы ошибкой. Вы не должны пытаться оптимизировать программу, прежде чем узнаете, где она медленная (преждевременная оптимизация - корень всех зол *
). Напишите свой код, затем запустите Devel :: NYTProf против него, чтобы найти, где он медленный. Если необходимо, перепишите эти части в XS или Inline::C
(я предпочитаю XS). Вы обнаружите, что вы выбираете правильную структуру данных быстрее, чем микрооптимизации, подобные этой.
*
Кнут, Дональд . Структурированное программирование с переходом к операторам , ACM Journal Computing Surveys , том 6, № 4, декабрь 1974. с.268.