구체적으로, 나는이 코드를 시도했다 :
package hello;
public class Hello {
Clock clock = new Clock();
public static void main(String args[]) {
clock.sayTime();
}
}
그러나 그것은 오류를 주었다
정적 메소드 main에서 비 정적 필드에 액세스 할 수 없음
그래서 나는 clock
이것으로 선언을 바꿨다 .
static Clock clock = new Clock();
그리고 효과가있었습니다. 해당 키워드를 선언 전에 두는 것은 무엇을 의미합니까? 해당 객체에 수행 할 수있는 작업과 관련하여 정확히 무엇을하고 /하거나 제한합니까?
답변
static
멤버는 특정 인스턴스 대신 클래스에 속합니다.
이는 클래스의 인스턴스를 백만 개 만들거나 만들지 않은 경우에도 하나의 static
필드 인스턴스 만 존재 한다는 것을 의미 합니다 [1] . 모든 인스턴스가 공유합니다.
static
메소드는 특정 인스턴스에 속하지 않기 때문에 인스턴스 멤버를 참조 할 수 없습니다. 주어진 예에서, main
어떤 Hello
클래스의 인스턴스 (따라서 Clock
클래스의 인스턴스 )를 참조해야하는지 알 수 없습니다. static
회원은 회원 만 참조 할 수 있습니다 static
. 인스턴스 멤버는 물론 static
멤버에 액세스 할 수 있습니다 .
참고 : 물론 static
멤버 는 객체 참조를 통해 인스턴스 멤버에 액세스 할 수 있습니다 .
예:
public class Example {
private static boolean staticField;
private boolean instanceField;
public static void main(String[] args) {
// a static method can access static fields
staticField = true;
// a static method can access instance fields through an object reference
Example instance = new Example();
instance.instanceField = true;
}
[1] : 런타임 특성에 따라 ClassLoader 또는 AppDomain 또는 스레드 당 하나 일 수 있지만 그 점이 아닙니다.
답변
“Hello”클래스의 개별 인스턴스마다 하나씩이 아니라 Hello에 “clock”인스턴스가 하나만 있다는 의미입니다. 따라서 모든 인스턴스간에 공통적으로 공유되는 “clock”참조가 하나 있음을 의미합니다. “Hello”클래스
따라서 코드의 어느 곳에서나 “새 Hello”를 수행해야하는 경우 : 첫 번째 시나리오 ( “정적”을 사용하지 않고 변경 전)에서 “새 Hello”를 호출 할 때마다 새 시계가 만들어집니다. 그러나 두 번째 시나리오 ( “정적”을 사용한 변경 후)의 B-에서는 모든 “새 Hello”인스턴스가 여전히 처음 작성된 초기 및 동일한 “시계”참조를 공유하고 사용합니다.
메인 외부의 “시계”가 필요하지 않으면 다음과 같이 작동합니다.
package hello;
public class Hello
{
public static void main(String args[])
{
Clock clock=new Clock();
clock.sayTime();
}
}
답변
static
키워드 수단은 무엇인가 (필드, 방법 또는 중첩 클래스)하는 관계가 형식 이 아닌 특정 인스턴스의 유형. 예를 들어, 클래스의 Math.sin(...)
인스턴스없이 호출 하면 Math
클래스 의 인스턴스를 만들 수 없습니다Math
.
자세한 정보는 관련 Oracle Java Tutorial 비트를 참조하십시오 .
사이드 노트
Java는 불행히도 정적 멤버가 인스턴스 멤버 인 것처럼 액세스 할 수 있습니다. 예 :
// Bad code!
Thread.currentThread().sleep(5000);
someOtherThread.sleep(5000);
즉, 만들어 보는 것처럼 sleep
인스턴스 방법이지만, 실제로는 정적 방법입니다 – 그것은 항상 현재의 thread의 잠을 수 있습니다. 호출 코드에서이를 명확하게하는 것이 좋습니다.
// Clearer
Thread.sleep(5000);
답변
static
Java 의 키워드는 변수 또는 함수가 실제 객체 자체가 아니라 유형에 속하는 해당 클래스의 모든 인스턴스간에 공유됨을 의미합니다 .
따라서 변수가 있고 한 인스턴스에서 변수 private static int i = 0;
를 늘리면 ( i++
) 모든 변경 사항이 모든 인스턴스에 반영됩니다. i
이제 모든 인스턴스에서 1이됩니다.
정적 메소드는 객체를 인스턴스화하지 않고 사용할 수 있습니다.
답변
정적 멤버의 기본 사용법 …
public class Hello
{
// value / method
public static String staticValue;
public String nonStaticValue;
}
class A
{
Hello hello = new Hello();
hello.staticValue = "abc";
hello.nonStaticValue = "xyz";
}
class B
{
Hello hello2 = new Hello(); // here staticValue = "abc"
hello2.staticValue; // will have value of "abc"
hello2.nonStaticValue; // will have value of null
}
이렇게하면 클래스 인스턴스 Hello를 다른 클래스로 보내지 않고 모든 클래스 멤버에서 값을 공유 할 수 있습니다. 정적 클래스는 클래스 인스턴스를 만들 필요가 없습니다.
Hello hello = new Hello();
hello.staticValue = "abc";
클래스 이름으로 정적 값이나 메소드를 호출 할 수 있습니다.
Hello.staticValue = "abc";
답변
정적은 클래스와 연결된 메서드 나 변수를 사용하기 위해 클래스의 인스턴스를 만들 필요가 없음을 의미합니다. 귀하의 예에서 다음을 호출 할 수 있습니다.
Hello.main(new String[]()) //main(...) is declared as a static function in the Hello class
직접 대신 :
Hello h = new Hello();
h.main(new String[]()); //main(...) is a non-static function linked with the "h" variable
정적 메서드 (클래스에 속함) 내에서는 정적이 아닌 멤버에 액세스 할 수 없습니다. 값은 클래스의 인스턴스화에 따라 달라지기 때문입니다. 인스턴스 멤버 인 비 정적 Clock 객체는 Hello 클래스의 각 인스턴스에 대해 다른 값 / 참조를 가지므로 클래스의 정적 부분에서 액세스 할 수 없습니다.
답변
자바 정적 :
정적은 비 액세스 수정 자입니다. 정적 키워드는 클래스의 인스턴스보다 클래스에 속합니다. 변수 또는 메소드를 클래스에 첨부하는 데 사용할 수 있습니다.
정적 키워드는 다음과 함께 사용할 수 있습니다.
방법
변하기 쉬운
다른 클래스 내에 중첩 된 클래스
초기화 블록
다음과 함께 사용할 수 없습니다 :
클래스 (중첩되지 않음)
건설자
인터페이스
메서드 로컬 내부 클래스 (차이와 중첩 클래스)
내부 클래스 메소드
인스턴스 변수
지역 변수
예:
생성자에서 증가한 count라는 인스턴스 변수 가있는 다음 예제를 상상해보십시오 .
package pkg;
class StaticExample {
int count = 0;// will get memory when instance is created
StaticExample() {
count++;
System.out.println(count);
}
public static void main(String args[]) {
StaticExample c1 = new StaticExample();
StaticExample c2 = new StaticExample();
StaticExample c3 = new StaticExample();
}
}
산출:
1 1 1
인스턴스 변수는 객체 생성시 메모리를 가져 오므로 각 객체는 인스턴스 변수의 복사본을 갖게되며, 증가하면 다른 객체에는 반영되지 않습니다.
이제 인스턴스 변수 수를 정적 변수 수로 변경 하면 프로그램에서 다른 출력을 생성합니다.
package pkg;
class StaticExample {
static int count = 0;// will get memory when instance is created
StaticExample() {
count++;
System.out.println(count);
}
public static void main(String args[]) {
StaticExample c1 = new StaticExample();
StaticExample c2 = new StaticExample();
StaticExample c3 = new StaticExample();
}
}
산출:
1 2 3
이 경우 정적 변수는 메모리를 한 번만 가져옵니다. 객체가 정적 변수의 값을 변경하면 해당 값을 유지합니다.
최종 정적 :
final 및 static으로 선언 된 전역 변수 는 전체 실행에서 변경되지 않은 상태로 유지됩니다. 정적 멤버는 클래스 메모리에 저장되며 전체 실행에서 한 번만로드되기 때문입니다. 클래스의 모든 객체에 공통입니다. 정적 변수를 final로 선언하면 모든 객체가 최종 값을 변경할 수 없습니다. 따라서 final 및 static으로 선언 된 변수를 상수라고도합니다. 인터페이스의 모든 필드는 기본적으로 최종적이고 정적이므로 상수라고합니다.
사진 자료 : 최종 정적