2008-11-14 21 views
74

Jak przekonwertować ciąg zawierający numer do jego wartości numerycznej w Perlu?Jak przekonwertować ciąg na liczbę w Perlu?

+3

Niektóre odpowiedzi są mylące, ponieważ pytanie zostało zmodyfikowane. Odpowiedź przez porquero jest najlepsza dla tej wersji pytania. – TimK

+0

Pytanie wymaga dalszych szczegółów. Czy ciąg składa się tylko z cyfr? Alfanumeryczne? Ok, czy alfy są rozebrane? Czy istnieje określony cel dla uzyskanej liczby? – JGurtz

Odpowiedz

83

Nie trzeba go przekształcić w ogóle:

% perl -e 'print "5.45" + 0.1;' 
5.55 
+18

5.55 nie jest liczbą całkowitą – OrangeDog

+13

@OrangeDog OP edytował pytanie (kilka miesięcy po opublikowaniu tej odpowiedzi) - oryginalne pytanie zawierało liczby zmiennoprzecinkowe. – Alnitak

+1

co z porównaniami, gdy ciąg ma przecinek? – Ramy

3

Perl naprawdę ma tylko trzy rodzaje: skalary, tablice i hashe. I nawet to rozróżnienie jest dyskusyjne. ;) Sposób, w jaki traktowana jest każda zmienna, zależy od tego, co robisz:

% perl -e "print 5.4 . 3.4;" 
5.43.4 


% perl -e "print '5.4' + '3.4';" 
8.8 
+4

Perl ma wiele więcej typów niż, ale dla pojedynczych wartości, to tylko pojedyncza wartość. –

+2

możesz również dodać 0 –

40

Perl jest językiem kontekstowym. Nie działa zgodnie z danymi, które mu dajesz. Zamiast tego wymienia sposób traktowania danych na podstawie operatorów, z których korzystasz, oraz kontekstu, w którym używasz tych danych. Jeśli zrobisz numery różne rzeczy, można uzyskać numery:

# numeric addition with strings: 
my $sum = '5.45' + '0.01'; # 5.46 

jeśli robisz ciągi różne rzeczy, masz ciągi:

# string replication with numbers: 
my $string = (45/2) x 4; # "22.522.522.522.5" 

Perl głównie domyśla się, co zrobić, i to przede wszystkim prawo. Innym sposobem na powiedzenie tego samego jest to, że Perl bardziej dba o czasowniki niż o rzeczowniki.

Czy próbujesz coś zrobić i to nie działa?

+0

Przebacz mi brak wiedzy tutaj, ale nie do końca dostaję twój drugi przykład. Dzielicie dwie liczby, a następnie je mnożysz, jak/dlaczego powoduje to ciąg znaków? – gideon

+4

Nie pomnażam liczb. 'X' jest operatorem replikacji ciągów. –

+1

oh Widzę. dzięki! :) Perl z pewnością ma wielu operatorów. – gideon

9

Google zaprowadził mnie tutaj podczas wyszukiwania tego samego pytania, które zadał phill (sortowanie spławikami), więc uznałem, że warto napisać odpowiedź pomimo tego, że wątek był trochę stary. Jestem nowicjuszem w Perl i wciąż mam owiniętą wokół niego głowę, ale oświadczenie Briana d Foy'a "Perl bardziej dba o czasowniki niż rzeczowniki". powyżej naprawdę uderza w gwóźdź w głowę. Przed zastosowaniem sortowania nie trzeba konwertować łańcuchów znaków na pływające obiekty. Musisz powiedzieć sortowi, aby posortować wartości jako liczby, a nie ciągi. tj

my @foo = ('1.2', '3.4', '2.1', '4.6'); 
my @foo_sort = sort {$a <=> $b} @foo; 

Zobacz http://perldoc.perl.org/functions/sort.html więcej szczegółów na temat sortowania

6

jak rozumiem int() nie jest przeznaczony jako funkcja „oddanych” za wyznaczenie typ danych to po prostu jest (ab), stosowane tutaj, aby określić kontekst jako arytmetyczna. Używałem (ab) (0 + val) w przeszłości, aby upewnić się, że $ val jest traktowane jako liczba.

54

Jest to proste rozwiązanie:

Przykład 1

my $var1 = "123abc"; 
print $var1 + 0; 

Wynik

123 

Przykład 2

my $var2 = "abc123"; 
print $var2 + 0; 

Wynik

0 
+5

AFAIU jest to jedyna odpowiedź na pytanie: – Cougar

+0

@Cougar: Zgadzam się. –

+1

Uwaga na dodanie zera do napisu. Jeśli ciąg zaczyna się od "inf" lub "nan", wartość nie będzie równa zero. E.g. my $ var2 = "info123"; print $ var2 + 0: Wynik będzie następujący: Inf –

1

W porównaniach robi różnicę, jeśli skalar jest liczbą ciągu. I nie zawsze jest to rozstrzygające.mogę zgłosić przypadek, gdy Perl pobierane pływaka w „naukowej” notacji i wykorzystywane w tym samym kilka linijek niżej w porównaniu:

use strict; 
.... 
next unless $line =~ /and your result is:\s*(.*)/; 
my $val = $1; 
if ($val < 0.001) { 
    print "this is small\n"; 
} 

I tu $val nie został zinterpretowany jako liczbową np "2e-77" pobrane z $line. Dodanie 0 (lub 0.0 dla dobrych programistów C) pomogło.

6
$var += 0 

Prawdopodobnie tego chcesz. Ostrzegamy jednak, jeżeli $ var jest ciąg nie może być zamieniony na numeryczny, dostaniesz błąd i $ var zostaną zresetowane do 0:

my $var = 'abc123'; 
print "var = $var\n"; 
$var += 0; 
print "var = $var\n"; 

kłody

var = abc123 
Argument "abc123" isn't numeric in addition (+) at test.pl line 7. 
var = 0 
0

Perl jest słabo napisany i oparty na kontekście. Wiele skalarów można traktować zarówno jako łańcuchy, jak i liczby, w zależności od operatorów, z których korzystasz. $a = 7*6; $b = 7x6; print "$a $b\n";
Otrzymujesz 42 777777.

Istnieje jednak subtelna różnica. Po odczytaniu danych numerycznych z pliku tekstowego do struktury danych, a następnie wyświetleniu go za pomocą Data::Dumper, zauważysz, że twoje liczby są cytowane. Perl traktuje je wewnętrznie jako struny.
Przeczytaj: $my_hash{$1} = $2 if /(.+)=(.+)\n/;.
przegubowe: 'foo' => '42'

Jeśli chcesz nienotowane numery w wysypisko:
lektura: $my_hash{$1} = $2+0 if /(.+)=(.+)\n/;.
przegubowe: 'foo' => 42

Po $2+0 Perl zauważa, że ​​już traktowane $ 2, jak liczby, ponieważ użyto operatora numerycznej.

Zauważyłem to podczas próby porównania dwóch skrótów z Data::Dumper.

Powiązane problemy