Zaokrąglanie podanej liczby do najbliższej ze zbioru

Zaokrąglanie podanej liczby do najbliższej ze zbioru
P2
  • Rejestracja: dni
  • Ostatnio: dni
  • Postów: 19
1

Witam, mam do napisania funkcję, która na wejściu dostaje liczbę naturalną z przedziału 0-360 i ma za zadanie zwrócić konkretne wartości:

Kopiuj
0, 90, 180, 270 i 360

w zależności od tego do której z tych liczb nasz input ma "najbliżej". Czyli:

Kopiuj
 f(1) = 0 f(47) = 90; f(136)=180

Jedyne co mi przychodzi do głowy to rozpisać cały przedział i sporządzić funkcję która będzie miała 5 instrukcji if..

Kopiuj
int f(int X)
{
    if(X > 0 && X <= 45) return 0;
    if(X > 45 && X <= 135) return 90;
    if(X > 135 && X <= 225) return 180;
    if(X > 225&& X <= 315) return 270;
    if(X > 315&& X <= 360) return 360;
}

Może jest jakiś sposób który byłby bardziej elegancki i wydajniejszy ?

szweszwe
  • Rejestracja: dni
  • Ostatnio: dni
  • Lokalizacja: Kraków
  • Postów: 1694
0

Pewnie jakoś tak:

Kopiuj
public static int f(int number) {
    number += 45;
    return 90 * (Math.round(number / 90));
}

Trzeba by to sprawdzić, ale ogólna idea zachowana, no i napisałem w Javie :]

ŁF
  • Rejestracja: dni
  • Ostatnio: dni
5
Kopiuj
angle = (int)((angle + 45 - (FLT_EPSILON * FLT_MIN)) / 90) * 90;

Ewentualnie uproszczona wersja (int)((angle + 44.999999) / 90) * 90;.
Ważne są dwie rzeczy

  • przetworzenie kąta na liczby naturalne 0, 1, 2 będące odpowiednikami tego, która to ćwiartka układu współrzędnych, uzyskasz to zaokrąglając w górę wynik dzielenia kąta przez 90; potem trzeba jeszcze tylko pomnożyć z powrotem przez 90;
  • oraz wcześniejsze "obrócenie" tego kąta o liczbę możliwie bliską 45' od dolnej strony. Czyli o (45 - eps)', gdzie eps to rozdzielczość Twojego typu zmiennoprzecinkowego, zwykle jest to bodajże float.

Zarejestruj się i dołącz do największej społeczności programistów w Polsce.

Otrzymaj wsparcie, dziel się wiedzą i rozwijaj swoje umiejętności z najlepszymi.