SEN1001 · 5. hafta · Methods

Metotlar: parametre, return, scope, overloading, Math ve Random

Metot başlığı, parametre ve argüman, return ile void, pass-by-value, kapsam (scope), aşırı yükleme (overloading), Math sınıfı ve rastgele sayı aralıkları. Vizedeki 'write a method' sorularının temeli.

methodmethod headerparameterargumentreturn typereturn statementvoidstatic methodmethod callpass-by-valuelocal variablescopemethod overloadingsignatureMath classRandomnextInt

Metot (method), bir işi yapan ve ismi olan bir kod bloğudur. Aynı işi on yerde yazmak yerine bir kez yazar, istediğin yerden çağırırsın. Vizede iki taraftan gelir: “bu çağrılar ne basar?” (içten dışa izleme, pass-by-value) ve “şu işi yapan bir metot yaz” (isPrime, sumDigits, max). İkincisinde başlığı doğru yazmak tek başına puan getirir.

Altın kurallar:

  1. Başlık şablonu: public static <dönüş tipi> <ad>(<parametreler>).
  2. void değilse her yolda return olmalı ve dönen değer tipe uymalı.
  3. return metodu anında bitirir.
  4. Pass-by-value: metot, çağıranın değişkenini değiştiremez.
  5. Overloading = aynı ad, farklı parametre listesi. Dönüş tipi tek başına yetmez.

Metot anatomisi

public static double average(int a, int b) {
    return (a + b) / 2.0;
}
ParçaBu örnekteAnlamı
erişim (access modifier)publicher yerden çağrılabilir
staticstaticnesne oluşturmadan, doğrudan çağrılır (main de static)
dönüş tipi (return type)doublemetodun geri verdiği değerin tipi; hiçbir şey vermiyorsa void
adaverageküçük harfle başlar, fiil gibi: computeTotal, isEven
parametre listesi(int a, int b)metodun dışarıdan aldığı değerler
gövde{ return ...; }işin yapıldığı yer

Parametre (parameter) başlıktaki değişkendir: a, b. Argüman (argument) çağrı sırasında verilen gerçek değerdir: average(3, 4) çağrısında 3 ve 4. Argümanların sayısı, sırası ve tipi parametrelerle uyuşmalı.

Bu derste metotlar main ile aynı sınıfa yazılır ve main’den çağrıldığı için static olur. Bir metodu tanımlamak onu çalıştırmaz; sadece çağrıldığında (call) çalışır.

return ve void

public static int twice(int n) { return n * 2; }
public static void greet(String name) { System.out.println("Hi " + name); }
public static int max(int a, int b) {
    if (a > b) return a;
    return b;
}
public static void line(int n, char c) {
    for (int i = 0; i < n; i++) System.out.print(c);
    System.out.println();
}
// main içinde:
System.out.println(twice(4));
greet("Deniz");
int t = twice(twice(3));     // içten dışa: twice(3) = 6, twice(6) = 12
System.out.println(t);
System.out.println(average(3, 4));
System.out.println(max(8, 11) + " " + max(5, 5));
line(5, '=');
8
Hi Deniz
12
3.5
11 5
=====
  • Değer döndüren metot bir ifadenin içinde kullanılır: yazdırılır, bir değişkene atanır ya da başka bir çağrıya argüman olur.
  • void metot bir iş yapar (yazdırmak gibi) ve hiçbir şey döndürmez. System.out.println(greet("x")) derlenmez.

Derleyicinin yakaladığı return hataları

static int f(int a) { return 2.5; }              // double, int'e sığmaz
static void g() { return 5; }                    // void değer döndüremez
static int h(int a) { if (a > 0) return 1; }     // a <= 0 iken return yok
Ret.java:2: error: incompatible types: possible lossy conversion from double to int
Ret.java:3: error: incompatible types: unexpected return value
Miss.java:2: error: missing return statement

missing return statement hatası şunu söyler: derleyici, koşul false olduğunda metodun ne döndüreceğini bilemiyor. Her olası yolun sonunda bir return olmalı.

Çağrı izleme ve pass-by-value

Bir metot çağrıldığında Java:

  1. Argümanları hesaplar.
  2. Değerlerini parametrelere kopyalar.
  3. Metodun gövdesini çalıştırır.
  4. return görünce değeri çağrının yapıldığı yere geri götürür.
public static void change(int x) {
    x = 100;
    System.out.println("inside: " + x);
}
// main içinde:
int a = 3;
change(a);
System.out.println("outside: " + a);
inside: 100
outside: 3

change’e a’nın kendisi değil, değeri (3) gitti. x = 100 sadece metodun kendi kopyasını değiştirdi. Buna pass-by-value denir ve Java’da her şey böyle geçer. (Dizilerde ve nesnelerde bu kuralın ilginç bir sonucu var; 6. ve 13. haftalarda göreceksin.)

Kapsam (scope)

Bir değişken sadece tanımlandığı blok { } içinde yaşar.

  • Metodun içinde tanımlanan değişken (local variable) başka metotta görünmez.
  • Parametreler de yereldir; metot bitince yok olur.
  • for başlığında tanımlanan sayaç döngüden sonra yoktur.
static void a() { int secret = 5; }
static void b() { System.out.println(secret); }
LocalScope.java:3: error: cannot find symbol

Farklı metotlarda aynı isimli değişkenler olabilir (main’de n, counter’da n); birbirleriyle ilgisizdirler.

Method overloading (aşırı yükleme)

Aynı sınıfta aynı isimde birden çok metot olabilir, yeter ki parametre listeleri (sayı, tip ya da sıra) farklı olsun. Metot adı ile parametre tiplerinin birleşimine imza (signature) denir.

static int add(int a, int b) { return a + b; }
static double add(double a, double b) { return a + b; }
static int add(int a, int b, int c) { return a + b + c; }
// main içinde:
System.out.println(add(2, 3));       // int, int
System.out.println(add(2.0, 3));     // double, int → 3 genişler → add(double, double)
System.out.println(add(1, 2, 3));    // üç argüman
5
5.0
6

Seçim kuralı: önce tam eşleşme aranır. Yoksa Java argümanı genişletebileceği en yakın tipe gider (int → long → float → double). Daraltma asla otomatik yapılmaz.

TUZAK · sadece dönüş tipi farklı. static int k(int a) ve static double k(int b) birlikte derlenmez: method k(int) is already defined. Parametre adı ve dönüş tipi imzaya dahil değildir.

Math sınıfı

Math’in metotları static’tir: Math.ad(...) diye çağrılır, import gerekmez.

System.out.println(Math.pow(3, 2));
System.out.println(Math.sqrt(16));
System.out.println(Math.max(4, 9) + " " + Math.min(4, 9));
System.out.println(Math.max(4, 9.0));
System.out.println(Math.abs(-3.5) + " " + Math.abs(-7));
System.out.println(Math.round(3.49) + " " + Math.round(3.5) + " " + Math.round(-2.5));
System.out.println(Math.ceil(2.1) + " " + Math.floor(2.9) + " " + Math.ceil(-2.1));
System.out.println(Math.PI);
9.0
4.0
9 4
9.0
3.5 7
3 4 -2
3.0 2.0 -2.0
3.141592653589793
MetotNe yaparDönüş tipi
Math.pow(a, b)a üzeri bher zaman double
Math.sqrt(x)karekökdouble
Math.abs(x)mutlak değerargümanın tipi
Math.max(a, b), Math.min(a, b)büyük, küçükargümanların tipi (biri double ise double)
Math.round(x)en yakın tam sayı, .5 yukarılong (double argümanla)
Math.ceil(x)yukarı yuvarladouble
Math.floor(x)aşağı yuvarladouble

TUZAK · Math.pow(2, 3) = 8 değil 8.0. Çıktı sorularında double dönen metotların .0 ile basıldığını unutma.

Math.round(-2.5) sonucu -2: “.5 yukarı” kuralı sayı doğrusunda yukarı, yani büyük olana doğru demek.

Rastgele sayılar

İki yol var:

import java.util.Random;
Random rand = new Random();
int die = rand.nextInt(6) + 1;                  // 1..6
int r = rand.nextInt(11) + 10;                  // 10..20
int m = (int) (Math.random() * 100) + 1;        // 1..100

Her ifade bir milyon kez çalıştırılınca görülen en küçük ve en büyük değerler:

1..6 10..20 1..100

Formül: min..max için rand.nextInt(max - min + 1) + min. nextInt(k) 0’dan k-1’e kadar k farklı değer üretir; + min aralığı kaydırır.

Math.random() 0.0 ile 1.0 arasında (1.0 hariç) bir double verir. Çarp, cast et, kaydır. Parantezin yeri kritik: (int) Math.random() * 100 her zaman 0’dır, çünkü cast çarpmadan önce yapılır.

Çözümlü örnek: yazma sorusu nasıl puan toplar

“isPrime yaz” gibi bir soruda kısmi puan şu sırayla gelir:

  1. Başlık: public static boolean isPrime(int n). Cevap evet/hayır ise dönüş tipi boolean.
  2. Özel durum: if (n < 2) return false;
  3. Döngü ve koşul: for (int i = 2; i * i <= n; i++) if (n % i == 0) return false;
  4. Döngüden sonra: return true;
  5. Kâğıt üstünde bir örnekle test: 9 için i = 2 (kalan 1), i = 3 (kalan 0) → false. Doğru.

TUZAK · return true’yu else’e koymak. if (n % i == 0) return false; else return true; yazarsan döngü ilk turda biter, sadece 2’ye bölünmeyi kontrol etmiş olursun. 9’a “asal” der.

Sık yapılan hatalar

Yanlış düşünceDoğrusu
Metodu tanımlamak onu çalıştırırSadece çağrılınca çalışır
Dönen değer otomatik bir yere yazılırAtamazsan ya da yazdırmazsan kaybolur
Metot içinde parametreyi değiştirmek main’i değiştirirPass-by-value, kopya değişir
return sonrası satırlar da çalışırMetot orada biter
void metottan return x;Sadece return; olabilir
Sadece dönüş tipi farklı iki metot = overloadingDerlenmez
Math.sqrt(16) → 44.0
Math.round(2.5) → 23
Zar için rand.nextInt(6)0..5 verir; + 1 ekle
(int) Math.random() * 6 + 1 zarHep 1; (int) (Math.random() * 6) + 1 yaz
Başka metodun değişkenine erişmekYerel değişken sadece kendi bloğunda

Kendini test et

Sınavdaki gibi İngilizce sorular. Önce kâğıt kalemle çöz, sonra cevabı aç.

Soru 1kolay

What is printed?

static int f(int x) { return x + 3; }
static int g(int x) { return f(x) * 2; }
// in main:
System.out.println(g(4));
Cevabı göster
14

g(4) önce f(4)'ü çağırır: 4 + 3 = 7. g'ye dönülür: 7 * 2 = 14. İçteki çağrı her zaman önce biter.

Soru 2kolay

What is printed?

static int mystery(int n) {
    int r = 0;
    for (int i = 1; i <= n; i++) {
        if (i % 2 == 1) r += i;
    }
    return r;
}
// in main:
System.out.println(mystery(6));
Cevabı göster
9

1'den 6'ya kadar tek sayıları toplar: 1 + 3 + 5 = 9.

Soru 3orta

What is printed?

static void swap(int a, int b) {
    int t = a; a = b; b = t;
    System.out.println("in swap: " + a + " " + b);
}
// in main:
int x = 5, y = 9;
swap(x, y);
System.out.println("in main: " + x + " " + y);
Cevabı göster
in swap: 9 5
in main: 5 9

Java pass-by-value çalışır: metoda x ve y'nin kopyaları gider. swap kendi kopyalarını değiştirir (9 5 basar) ama main'deki x ve y'ye dokunamaz.

Soru 4orta

What is printed?

static int early(int n) {
    if (n > 5) return 1;
    System.out.println("small");
    return 0;
}
// in main:
System.out.println(early(8));
System.out.println(early(2));
Cevabı göster
1
small
0

early(8): 8 > 5 → return 1, metot anında biter, small basılmaz. early(2): koşul false, small basılır, sonra 0 döner ve main onu basar.

Soru 5orta

What is printed?

static int counter(int n) {
    n++;
    return n;
}
// in main:
int n = 10;
n = counter(n);
counter(n);
System.out.println(n);
Cevabı göster
11

İlk çağrının sonucu (11) n'ye atanır. İkinci çağrı 12 döndürür ama sonuç hiçbir yere atanmadığı için kaybolur. main'deki n 11 kalır.

Soru 6orta

What is printed?

static void show(int x)    { System.out.println("int: " + x); }
static void show(double x) { System.out.println("double: " + x); }
static void show(String s) { System.out.println("String: " + s); }
// in main:
show(7 / 2);
show(7 / 2.0);
show("" + 7 / 2);
Cevabı göster
int: 3
double: 3.5
String: 3

Önce argüman hesaplanır, sonra tipine göre metot seçilir. 7 / 2 = 3 (int) → show(int). 7 / 2.0 = 3.5 (double) → show(double). "" + 7 / 2: önce bölme (3), sonra birleştirme → "3" String → show(String).

Soru 7zor

Only these two overloads exist. What is printed?

static void p(double d) { System.out.println("double " + d); }
static void p(long l)   { System.out.println("long " + l); }
// in main:
p(5);
p(5.0f);
Cevabı göster
long 5
double 5.0

p(int) yok. Java int argümanı genişletebileceği (widening) en yakın tipe gönderir: int → long, double'dan önce gelir. 5.0f bir float; long'a gidemez (daraltma), double'a genişler.

Soru 8orta

What is printed?

System.out.println(Math.pow(2, 3) + Math.max(2, 3));
System.out.println(Math.sqrt(25) + " " + Math.abs(-4) + " " + Math.round(2.5));
System.out.println(Math.ceil(4.1) + " " + Math.floor(4.9) + " " + (int) Math.ceil(4.1));
Cevabı göster
11.0
5.0 4 3
5.0 4.0 5

pow her zaman double döner: 8.0 + 3 = 11.0. sqrt da double: 5.0. abs ve max argümanın tipini korur: 4. round(2.5) en yakın tam sayı, .5 yukarı: 3. ceil/floor double döner: 5.0, 4.0. Cast ile int'e çevrilince 5.

Soru 9orta

What is printed?

static int square(int x) { return x * x; }
static int twice(int n)  { return n * 2; }
static int max(int a, int b) { if (a > b) return a; return b; }
// in main:
System.out.println(square(square(2)) + square(3));
System.out.println(max(square(3), twice(5)));
Cevabı göster
25
10

square(2) = 4, square(4) = 16, square(3) = 9, 16 + 9 = 25. İkinci satır: max(9, 10) = 10.

Soru 10orta

Assume Random rand = new Random();. Which values can each expression produce? (a) rand.nextInt(6) + 1 (b) rand.nextInt(5) + 3 (c) (int) (Math.random() * 10) (d) (int) Math.random() * 10

Cevabı göster
(a) 1..6 (b) 3..7 (c) 0..9 (d) always 0

nextInt(k) 0 ile k-1 arası verir. (a) 0..5 + 1. (b) 0..4 + 3. (c) Math.random() 0.0 ≤ x < 1.0, × 10 → 0.0..9.99, cast → 0..9. (d) Cast önce Math.random()'a uygulanır: (int) 0.73 = 0, 0 * 10 = 0. Doğrulamada 1000 denemenin toplamı 0 çıktı.

Soru 11orta

Write a static method isPrime(int n) that returns true if n is prime. Numbers less than 2 are not prime.

Cevabı göster
if (n < 2) return false; for (int i = 2; i * i <= n; i++) if (n % i == 0) return false; return true;

Bölen ararsın; bir tane bulmak yeter. return true döngünün dışında olmalı: ancak hiç bölen bulunmazsa çalışır.public static boolean isPrime(int n) { if (n < 2) return false; for (int i = 2; i * i <= n; i++) { if (n % i == 0) return false; } return true;}1..30 arası asallar: 2 3 5 7 11 13 17 19 23 29. isPrime(49) → false, isPrime(97) → true. i * i <= n yerine i < n yazmak da doğrudur, sadece daha yavaş.

Soru 12orta

Write a static method sumDigits(int n) that returns the sum of the digits of a non-negative integer, using a while loop. Example: sumDigits(4823) returns 17.

Cevabı göster
while (n > 0) { sum += n % 10; n /= 10; } return sum;

% 10 son basamağı verir, / 10 siler. n 0 olunca basamak kalmamıştır.public static int sumDigits(int n) { int sum = 0; while (n > 0) { sum += n % 10; n /= 10; } return sum;}Test: 4823 → 17, 309 → 12, 7 → 7, 0 → 0 (döngüye hiç girilmez).

Doğrulama: Tüm çıktılar JDK 26 ile çalıştırıldı (verify/SEN1001/W05.java). Random aralıkları 1.000.000 denemeyle gözlendi (min..max). Derleme hataları verify/SEN1001/err/Ret.java, Miss.java ve LocalScope.java javac ile alındı.

Deftere not kartı

public static dönüşTipi ad(tip p1, tip p2) { ... return değer; } void → değer döndürmez; void'de return 5; derlenmez (unexpected return value) int dönen metotta return 2.5; → lossy conversion if dalında return eksik → missing return statement Parametre = başlıktaki değişken Argüman = çağrıdaki değer sayı, sıra, tip uymalı return metodu ANINDA bitirir, alttakiler çalışmaz İçteki çağrı önce: g(f(2)) dönen değeri kullanmazsan kaybolur Pass-by-value: metoda KOPYA gider, main'deki değişken değişmez Scope: değişken tanımlandığı { } içinde yaşar; başka metodun yerel değişkeni görünmez Overloading: aynı ad, farklı parametre listesi (sayı/tip/sıra). Sadece dönüş tipi farkı → derlenmez Seçim: tam eşleşme, yoksa genişletme int → long → float → double Math.pow, sqrt, ceil, floor → double abs, max, min → tipi korur round(2.5)=3 round(-2.5)=-2 Random rand = new Random(); import java.util.Random; min..max: rand.nextInt(max - min + 1) + min zar: nextInt(6) + 1 (int)(Math.random() * n) → 0..n-1 (int) Math.random() * n → hep 0