자바의 변수에는 사용할 수 있는 범위(scope)가 있습니다.
코드를 작성하는 곳이 어디냐에 따라 사용할 수 있는 변수가 달라집니다.
자바에는 다음 세 종류의 변수가 있으며 각자 유효범위가 다릅니다.
지역변수 int i를 선언하게 되면 해당 메소드 안에서만 사용할 수 있는 변수가 되기 때문에 for문에 있는 a메소드의 i값은 적용되지 않습니다.
public class ScopeDemo {
static void a() {
//지역변수 i선언
//a메소드안에 i값은 해당 메소드 안에서만 사용할 수 있다.
int i=0;
}
public static void main(String[] args) {
for(int i=0; i<5; i++) {
a();
System.out.println(i);
}
}
}
결과:
0
1
2
3
4
아래 예제를 보면 a메소드안에 i값은 아무것도 선언이 안되어있기 때문에 밖에도 영향을 미칩니다. 따라서 for문에 값이 할당되기 때문에 계속 0이 출력되면서 무한루프에 빠지게 됩니다.
package org.scope;
public class ScopeDemo2 {
//전역변수 i선언
static int i;
static void a() {
//i를 선언하진 않고 할당만했음
i=0;
}
public static void main(String[] args) {
//선언은 하지 않고 i라는 값만 할당만했음
for(i=0; i<5; i++) {
a();
System.out.println(i);
}
}
}
아래 예제에서는 a메소드에 전역변수를 선언하면서 정상적인 값을 호출하게 됩니다.
지역적인 것이 전역적인 것보다 우선순위가 높습니다.
public class ScopeDemo2 {
//전역변수 i선언
static int i;
static void a() {
//지역변수 i선언
int i=0;
}
public static void main(String[] args) {
//지역변수 i할당됨
for(i=0; i<5; i++) {
a();
System.out.println(i);
}
}
}
결과 :
0
1
2
3
4
아래 예제에서는 b라는 메소드의 지역변수 i=30 값이 출력됩니다.
(만약 지역변수 i=30이 없다면 전역변수 static int i=5가 출력)
public class ScopeDemo6 {
static int i=5; //전역변수
static void a() {
int i=10; //지역변수
b();
}
static void b() {
int i=30;
//b라는 메소드의 지역변수 i의 값 30호출
System.out.println(i);
}
public static void main(String[] args) {
int i=1;
a();
}
}
결과:
30
메소드 m에서 전역변수와 이름이 같은 지역변수를 선언하고나서 v를 그대로 출력하면 우선순위가 높은 지역변수가 호출됩니다. 지역변수가 아닌 전역변수를 호출하고 싶으면 뒤에 this를 붙입니다. this가 붙으면 그 객체에 대한 전역 유효범위를 의미합니다.
class C{
int v=10;
void m() {
int v=20;
//지역변수 v=20 값이 호출됨
System.out.println(v);
//전역변수 v=10값이 호출됨
System.out.println(this.v);
}
}
public class ScopeDemo7 {
public static void main(String[] args) {
//C라는 클래스의 인스턴스를 c1이라는 변수에 담겠다.
C c1=new C();
c1.m();
}
}
class Calculator{
static double PI=3.14;
int left,right;
public void setOperands(int left,int right) {
//this.변수는 전역변수를 나타내며 오른쪽의 left는 지역변수를 나타냅니다.
this.left=left;
this.right=right;
}
public void sum() {
System.out.println(this.left+this.right);
}
}
public class CalculatorDemo1 {
public static void main(String[] args) {
Calculator c1=new Calculator();
System.out.println(c1.PI);
Calculator c2=new Calculator();
System.out.println(c2.PI);
System.out.println(Calculator.PI);
}
}
결과:
3.14
3.14
3.14
뒤에 this없이도 자바에서는 전역변수 left,right가 있는지 없는지 찾아내서 사용합니다.
class Calculator{
static double PI=3.14;
int left,right;
public void setOperands(int _left,int _right) {
//this.변수는 전역변수를 나타내며 오른쪽의 left는 지역변수를 나타냅니다.
//뒤에 this안붙여도 자바에서 전역변수의 left와 right가 있는지 찾아내기 때문에 아래방법도 옳바른표현이다.
left=_left;
right=_right;
}
public void sum() {
System.out.println(this.left+this.right);
}
}
public class CalculatorDemo1 {
public static void main(String[] args) {
Calculator c1=new Calculator();
System.out.println(c1.PI);
Calculator c2=new Calculator();
System.out.println(c2.PI);
System.out.println(Calculator.PI);
}
}
1) public static main 함수에서 사용되는 변수는 static형 전역변수만 가능한 걸까요?
아니면, dynamic형 전역변수도 this를 이용해서 접근 할 수 있을지 궁금하네요.
2) static이 붙지 않은 함수는 static이 붙던 안붙던 전역변수는 다 건들 수 있을까요?
3) this 생략 가능한 경우는, 함수 내에 전역변수와 같은 이름의 지역변수를 사용하지 않을 때. 하지만, 코드의 가독성을 위해 this는 반드시 쓰는게 좋겠습니다.