program story

변수는 내부 클래스 내에서 액세스됩니다.

inputbox 2020. 8. 11. 08:24
반응형

변수는 내부 클래스 내에서 액세스됩니다. 최종 선언 필요


그래서 제목은 모든 것을 말합니다. .NET 내부에서 컴파일 오류가 발생 onClick합니다.

여기에 코드가 있습니다.

public class fieldsActivity extends Activity {

Button addSiteButton;
Button cancelButton;
Button signInButton;


/**
 * Called when the activity is first created.
 */
@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    // to create a custom title bar for activity window
    requestWindowFeature(Window.FEATURE_CUSTOM_TITLE);

    setContentView(R.layout.fields);
    // use custom layout title bar
    getWindow().setFeatureInt(Window.FEATURE_CUSTOM_TITLE, R.layout.topbar);

    Pager adapter = new Pager();
    ViewPager mPager = (ViewPager) findViewById(R.id.fieldspager);
    mPager.setAdapter(adapter);
    mPager.setCurrentItem(1);



    addSiteButton = (Button) findViewById(R.id.addSiteButton);
    addSiteButton.setOnClickListener(new View.OnClickListener() {

        @Override
        public void onClick(View v) {
           mPager.setCurrentItem(2, true); //Compilation error happens here.
        }


    });


    cancelButton = (Button) findViewById(R.id.cancel_button);
    signInButton = (Button) findViewById(R.id.sign_in_button);

}

최종적으로 만들고 싶지 않다면 항상 전역 변수로 만들 수 있습니다.


변수를 final로 선언하거나 인스턴스 (또는 전역) 변수로 만들 수 있습니다. 최종적으로 선언하면 나중에 변경할 수 없습니다.

메서드에 정의되고 익명 내부 클래스에서 액세스하는 모든 변수는 최종 변수 여야합니다. 그렇지 않으면 내부 클래스에서 해당 변수를 사용할 수 있습니다. 변수가 내부 클래스에서 변경된 다음 나중에 엔 클로징 범위에서 사용되는 경우 내부 클래스에서 변경 한 내용이 엔 클로징 범위에서 지속되지 않는다는 사실을 알지 못합니다. 기본적으로 내부 클래스에서 일어나는 일은 내부 클래스에 남아 있습니다.

여기에 더 자세한 설명을 썼습니다 . 또한 인스턴스 및 전역 변수를 final로 선언 할 필요가없는 이유도 설명합니다.


오류는 모든 것을 말합니다.

ViewPager mPager = (ViewPager) findViewById(R.id.fieldspager);

final ViewPager mPager = (ViewPager) findViewById(R.id.fieldspager);

여기에 재미있는 대답이 있습니다.

최종 단일 요소 배열을 선언하고 배열의 요소를 원하는대로 변경할 수 있습니다. 이 컴파일러 규칙이 처음에 구현 된 바로 그 이유를 깨뜨릴 것이라고 확신하지만, 오늘처럼 타임 바인드에있을 때 편리합니다.

나는 실제로 이것에 대한 크레딧을 청구 할 수 없습니다. IntelliJ의 추천이었습니다! 약간 험난한 느낌입니다. 그러나 전역 변수만큼 나쁘지는 않아서 여기서 언급 할 가치가 있다고 생각했습니다. 문제에 대한 하나의 해결책 일뿐입니다. 반드시 최고의 것은 아닙니다.

final int[] tapCount = {0};

addSiteButton.setOnClickListener(new View.OnClickListener() {

    @Override
    public void onClick(View v) {
       tapCount[0]++;
    }

});

@Veger가 말했듯 final이 변수를 내부 클래스에서 사용할 수 있도록 만들 수 있습니다.

final ViewPager pager = (ViewPager) findViewById(R.id.fieldspager);

I called it pager rather than mPager because you are using it as a local variable in the onCreate method. The m prefix is cusomarily reserved for class member variables (i.e. variables that are declared at the beginning of the class and are available to all class methods).

If you actually do need a class member variable, it doesn't work to make it final because you can't use findViewById to set its value until onCreate. The solution is to not use an anonymous inner class. This way the mPager variable doesn't need to be declared final and can be used throughout the class.

public class MainActivity extends AppCompatActivity {

    private ViewPager mPager;
    private Button mButton;

    @Override
    public void onCreate(Bundle savedInstanceState) {
        // ...

        mPager = (ViewPager) findViewById(R.id.fieldspager);

        // ...

        mButton.setOnClickListener(myButtonClickHandler);
    }


    View.OnClickListener myButtonClickHandler = new View.OnClickListener() {
        @Override
        public void onClick(View view) {
            mPager.setCurrentItem(2, true);
        }
    };
}

참고URL : https://stackoverflow.com/questions/14425826/variable-is-accessed-within-inner-class-needs-to-be-declared-final

반응형