Pure Java – 94 – Development – Using Classpaths

Merhaba Arkadaslar
Bu bolumde classpath kavramini ve package yapisi ile kullanimini inceleyecegiz.

Bir onceki yazida javac ve java komutlarinini komut satirinda kullandik. Orneklerimizde java.lang kutuphanesini ve java.util kutuphanesini kullandik. Aslinda Java arka planda bizim icin bu paketleri buldu ve biz ilgili siniflarin yerini belirtmeden kodumuz sorunsucaz derlendi ve calisti.

javac ve java komutlarinin searching konusunda ayni algoritmalari ve yaklasimlari vardir.

  • Ilk olarak Core Java classlarinin bulundugu dizine/directory bakarlar.
  • Ilgili sinif bulundugu zaman aramayi sonlandirirlar.
  • Ikinci olarak baktiklari yer classpath’lerle belirtilmis dizinlerdir.
  • classpath , ‘siniflari bulmak icin arama yapilacak dizin’ olarak tarif edilebilir. classpath’ler 2 sekilde tanimlanabilir.
  1. Operating System Environment variable
  2. Command-line option’i olarak

Command-line da tanimlanan classpath bilgisi Operating System Environment olarak tanimlanan classpath bilgisini override eder , fakat Command line sadece ilgili calistirma/cagrisim (invocation) icin gecerlidir.

classpath declaration
classpath directory/dizin bilgisini icerir, bu bilgiyi delimiter(ayirici) ile yazabiliriz. Unix-based isletim sistemlerinde dizinler icin / , delimiter olarak : kullanilir.

-classpath /com/foo/acct:/com/foo

Burada 2 tane dizin/directory belirtiyoruz.

/com/foo/act ve /com/foo

Bu dizinler/directory / ile basladigi icin absolute path olarak isimlendirilir.

Burada onemli nokta; bir subdirectory/alt dizin belirttigimizde ust dizini belirtmis olmayiz.
Yani /com/foo/act ve /com/foo dizinleri arama yapilacak dizin olarak kullanilirken /com dizininde arama yapilmayacaktir.

Sinavda dikkat edilmesi gereken bir nokta Unix convention’a uyulmasidir. Yani Windowsta path \ seklinde olurken Unix – based olarak / kullanilmaktadir. Bununla birlikte delimiter da windowsta ; olurken unix te : seklindedir.

Arama/Searching yapilirken java ve javac komutlari current directory varsayilan olarak aranmaz. Bunun icin ozellikle belirtmemiz gereklidir. nokta(.) karakterini kullanarak mevcut/current directory ara diyebiliriz.

-classpath /com/foo/acct:/com/foo:.

Bu classpath bilgisi bir onceki bilgi ile benzerdir fakat tek farki en sona eklenen .(nokta) path bilgisidir. Boylelikle arama isleminde current directory de kullanilacak.

Bir diger onemli nokta olarak arama islemi soldan saga dogru olur.

-classpath /com:/foo:.

-classpath .:/foo:/com

Bu iki classpath ayni anlama gelmez. Birincisinde ilk olarak /com dizininden baslanarak arama yapilir. Ikincinde ise once . (nokta) yani mevcut directoryden aranmaya baslanir.

Ornegin Test.class sinifimizin /com ve .(nokta) da oldugunu varsayalim. Birinci classpath /com da olan sinifi bulacak ve aramayi sonlandiracaktir. Ikinci classpath mevcut dizindeki Test.class dosyasini bulacak ve aramayi sonlandiracaktir.

Son olarak -classpath yerine -cp de kullanilabilir fakat -cp tutarsizliklara neden olabilir(inconsistent). Bir cok JVM destekler fakat -cp nin bir garantisi yoktur.

Packages & Searching
Isin isine package tanimlari ve classpath girdigi zaman sinavda dikkat edilmesi gereken noktalar ortaya cikmatakdir.

Simdi com/foo dizininde MyClass.java dosyasi olusturalim ;

package com.foo;

public class MyClass {
	public void hi() {
	}
}

Bu basit kod orneginde, MyClass com.foo package/paketinin bir uyesidir diyoruz. Bunun anlami sinifimizin full qualified ismi com.foo.MyClass seklindedir.

Bir sinif package icerisindeyse package ismi full qualified isminin bir parcasidir ve bu isim bolunemez atomic bir ozellige sahiptir.

Bir baska sinifta bu sinifi import edelim;

import com.foo.MyClass;
import com.foo.*;

public class Another {
	void go() {
		MyClass m1 = new MyClass(); // alias name
		com.foo.MyClass m2 = new com.foo.MyClass(); // full name
		m1.hi();
		m2.hi();
	}
}

Relative & Absolute Paths
classpath , bir yada daha fazla path bilgisinden olusur. classpath’te yer alan her bir path absolute ya da relative path olabilir.
Unix’te absolute path / (forward slash) ile baslar. (root) Windowsta ise c:\ olarak baslar. Sinavda unix based baz alinmaktadir.

/ (forward slash) sistemin root dizinini gosterir. Soz konusu absolute path oldugunde current directory onemli degildir , absolute path her zaman root’u baz aldigi icin hangi dizinde oldugumuzun bir onemi yoktur.

relative path ise / (forward slash) ile baslamaz.

/ (root)
|
|---- dirA
    |
    |---- dirB
        |
        |---- dirC

-cp dirB:dirB/dirC

dirB ve dirB/dirC pathleri / ile baslamadigi icin relative path’dir. Bu 2 relative path sadece current directory dirA oldugunda bir anlam kazanacaktir.

current directory dirA oldugunda dirB ve dirC dizinleri search edilir. dirA search edilmez, cunku classpath de .(nokta) karakteri yer almamaktadir.

current directory root olsaydi dirB ya da dirC search edilmezdi. Cunku dirB root’un direkt olarak alt dizini degildir.
current directory dirB olsaydi yine dirB ya da dirC search edilmezdi. cunku dirB dizini dirB isimli bir alt dizine sahip degil !
dirB dizini altinda dirB ve dirB/dirC seklinde klasor olsaydi bu durumda current directory ustteki dirB olsaydi

-cp dirB:dirB/dirC

alt dirB ve dirC yi search edecekti.

Bir diger ornek olarak

/ (root)
|
|---- dirA
    |
    |---- dirB
        |
        |---- dirC

-cp /dirB:/dirA/dirB/dirC

current directory dirA olsaydi hangi dizinler search edilecekti ? ya da root olsaydi ya da dirB ?
dikkat edelim classpath’te verilen pathler relative path degildir ! bu pathler / ile basladigi icin absolute path‘tir.
Soz konusu absolute path oldugunda hangi dizinde oldugumuzun bir onemi yoktur. absolute path’i bir nevi root’a gore relative olarak dusunebiliriz. Cunku mevcut dizin onemsiz olmakta ve root’u baz almaktadir.

/dirB gecersiz bir dizin olacaktir ve dirB dizini search edilmeyecektir. Cunku dirB root’un direkt olarak alt dizini degildir.

/dirA/dirB/dirC gecerli bir dizin olacaktir ve dirC dizini search edilecektir.
Burada nokta(.) da kullanilmadigi icin mevcut dizin de search edilmeyecektir.

myProject/src dizininde

A sinifi

public class A {}

B sinifi

public class B extends A{}

src dizininde

javac B.java

myProject/src/test dizininde

A sinifi

package test;
public class A { }

B sinifi

package test;
public class B extends A { }

 

myProject dizininde

javac src/test/B.java

hata verir!

src\test\B.java:2: cannot find symbol
symbol: class A
public class B extends A{}→

test.A.java sinifini bulmasi icin classpath kullanmaliyiz

javac -cp src src/test/B.java

src/test2/pack1
A sinifi

package test2.pack1;
public class A {}

src/test2/pack2
B sinifi

package test2.pack2;
import test2.pack1.A;
public class B extends A{}

src dizininde;

javac test2/pack2/B.java

myProject dizininde

javac -cp src src/test2/pack2/B.java

myProject/foo dizininde

javac -cp ../src ../src/test2/pack2/B.java

Yazimi burada sonlandiriyorum.
Herkese Bol Javali Gunler dilerim.
Be an oracle man , import java.*;
Levent Erguder
OCP, Java SE 6 Programmer
OCE, Java EE 6 Web Component Developer

Print Friendly, PDF & Email

Leave a Reply

Your email address will not be published. Required fields are marked *