2010-03-02 19 views
17

Spędziłem część wczorajszego i dzisiejszego dnia wyszukując błąd w jakimś kodzie Matlaba. Myślałem, że mój problem jest indeksowany (z wieloma strukturami, których nie zdefiniowałem i wciąż się do tego przyzwyczaiłem), ale okazało się, że to błąd przepełnienia. Brakowało mi tego za bardzo konkretnego powodu:Jak rozpoznać błędy przepełnienia w programie Matlab?

>> uint8(2) - uint8(1) 

ans = 

    1 

>> uint8(2) - uint8(2) 

ans = 

    0 

>> uint8(2) - uint8(3) 

ans = 

    0 

Liczyłam ostatni być coś -1 (lub 255). W środku dużego wektora trudno było wykryć błędne, ale 255 łatwo by się wyróżniało.

Jakieś wskazówki, jak łatwo wykryć te problemy w przyszłości? (Idealnie, chciałbym wyłączyć sprawdzanie przepełnienia, aby działało jak C.) Zmiana na double działa, oczywiście, ale jeśli nie zdaję sobie sprawy, że to jest uint8 na początek, to nie pomaga.

+1

Skąd te numery z? Jeśli załadujesz je z pliku, możesz po prostu dodać linię do programu ładującego, aby albo zwrócić wszystko jako uint8, albo jako podwójne. Inaczej niż przez czytanie plików, nie powinieneś spodziewać się uint8 w Matlabie. – Jonas

+0

Właściwie nie wiem dokładnie, skąd pochodzą. Integruje się z czyimś kodem, więc nie znam szczegółów. –

Odpowiedz

13

Można zacząć od włączenia ostrzeżenia całkowitych:

intwarning('on') 

To daje ostrzeżenie, gdy całkowita przepełnienie.

Pamiętaj jednak, zgodnie z opisem here, powoduje to spowolnienie arytmetyczne liczby całkowitej, więc używaj tego tylko podczas debugowania.

+3

Uwaga: [INTWARNING został już usunięty] (http://www.mathworks.com/help/techdoc/rn/bsdgysw-1.html#bseu09-1), a powyższy link jest już nieprawidłowy. – gnovice

+0

Czy wiecie, dlaczego został usunięty i jak go użyć? – Lupocci

6

Począwszy uwalnianiu R2010b, a później, w zależności INTWARNING has been removed wraz z these warning messages for integer math and conversion:

  • MATLAB:intConvertNaN
  • MATLAB:intConvertNonIntVal
  • MATLAB:intConvertOverflow
  • MATLAB:intMathOverflow

Stosowanie INTWARNING nie jest więc realną opcją do określania, kiedy występują przepełnienia całkowite. Alternatywą jest użycie funkcji CLASS w celu przetestowania klasy danych i przekształcenia jej odpowiednio przed wykonaniem operacji. Oto przykład:

if strcmp(class(data),'uint8') %# Check if data is a uint8 
    data = double(data);   %# Convert data to a double 
end 

Można również użyć funkcji ISA także:

if ~isa(data,'single') %# Check if data is not a single 
    data = single(data); %# Convert data to a single 
end 
+2

Jeśli nie wiesz, skąd pochodzą dane, zdecydowanie powinieneś wykonać bardzo ostrożne testy wejściowe w ten sposób. – Jonas

+0

@ gnovice Po prostu wpadłem na ten sam problem, ale twoje podejście do rzucania na podwójne lub pojedyncze wydaje mi się bardzo dziwne. Co jeśli potrzebuję tych uintów? Nie chcę być zmuszany do robienia wszystkiego w grze podwójnej. Oczywiście nie jest to dla ciebie pytanie, ale dlaczego MATLAB nie może używać standardowych liczb całkowitych bez znaku? – angainor

Powiązane problemy