문제

가능한 복제 :
Java는 "Pass-by-reference"입니까?

오늘은 비정상적인 Java 방법을 찾았습니다.

private void addShortenedName(ArrayList<String> voiceSetList, String vsName)
{
     if (null == vsName)
       vsName = "";
     else
       vsName = vsName.trim();
     String shortenedVoiceSetName = vsName.substring(0, Math.min(8, vsName.length()));
     //SCR10638 - Prevent export of empty rows.
     if (shortenedVoiceSetName.length() > 0)
     {
       if (!voiceSetList.contains("#" + shortenedVoiceSetName))
         voiceSetList.add("#" + shortenedVoiceSetName);
     }
}

변수, 복잡한 객체 여부에 대한 Java의 행동에 대해 내가 읽은 모든 것에 따르면,이 코드는 정확히 아무것도하지 않아야합니다. 그래서 음 ... 여기서 뭔가 빠졌나요? 나에게 잃어버린 미묘함이 있습니까, 아니면이 코드가 thedailywtf에 속합니까?

도움이 되었습니까?

해결책

Rytmis가 말했듯이 Java는 가치별로 참조를 통과합니다. 이것이 의미하는 바는 메소드의 매개 변수에서 돌연변이 메소드를 합법적으로 호출 할 수 있지만 재 할당 할 수는 없으며 값이 전파 될 것으로 기대할 수는 없습니다.

예시:

private void goodChangeDog(Dog dog) {
    dog.setColor(Color.BLACK); // works as expected!
}
private void badChangeDog(Dog dog) {
    dog = new StBernard(); // compiles, but has no effect outside the method
}

편집하다: 이 경우 이것이 의미하는 바는 그렇습니다 voiceSetList ~할 것 같다 이 방법의 결과로 변경 (새로운 요소가 추가 될 수 있음) vsName 방법 외부에서는 보이지 않습니다. 혼란을 방지하기 위해 종종 내 메소드 매개 변수를 표시합니다. final,이 방법은 메소드 내부에서 (실수로 또는 그렇지 않음) 재 할당되지 않도록합니다. 이것은 두 번째 예제가 컴파일하는 것을 막을 것입니다.

다른 팁

자바가 통과합니다 가치 별 참조, 따라서 참조 사본을 얻지 만 참조 된 객체는 동일합니다. 따라서이 메소드는 입력 목록을 수정합니다.

참조 자체는 가치에 따라 전달됩니다.

Java How to Program, 4th Edition by Deitel & Deitel : (pg. 329)

다른 언어와 달리 Java는 프로그래머가 각 인수를 값 또는 참조로 전달할지 여부를 선택할 수 없습니다. 원시 데이터 유형 변수는 항상 값으로 전달됩니다. 객체는 방법으로 전달되지 않습니다. 오히려 객체에 대한 참조는 메소드로 전달됩니다. 참조 자체는 값으로 전달됩니다. 참조 사본은 메소드로 전달됩니다. 메소드가 객체에 대한 참조를 수신하면 메소드는 객체를 직접 조작 할 수 있습니다.

대학에서 Java를 학습 할 때이 책을 사용했습니다. 훌륭한 참조.

여기에 설명하는 좋은 기사가 있습니다.http://www.javaworld.com/javaworld/javaqa/2000-05/03-qa-0526-pass.html

글쎄, 그것은 그것을 조작 할 수 있습니다 ArrayList - 객체입니다 ... 객체 참조를 전달하는 경우 (값으로 전달) 해당 객체의 변경 사항은 발신자에게 반영됩니다. 그게 질문인가요?

vsname이 수정 되었기 때문에 당신이 혼란스러워한다고 생각합니다. 그러나 이러한 맥락에서, 그것은 단지 로컬 변수 일 뿐이며 ShortenedVoicesEtname과 동일한 수준입니다.

코드 내 정확한 질문이 무엇인지는 명확하지 않습니다. Java는 통과 별이지만 배열은 객체가 아니라 포인터 만 통과 할 때 통과 할 수 있습니다! 배열은 실제 물체가 아닌 포인터로 구성됩니다. 이것은 그것들을 매우 빠르게 만들지 만 처리하기에 위험합니다. 이것을 해결하려면 사본을 얻기 위해 복제해야하며, 심지어 배열의 첫 번째 차원 만 복제합니다.

자세한 내용은 내 답변을 참조하십시오. Java에서는 얕은 사본이란 무엇입니까? (또한 내 다른 답변을 참조하십시오)

그건 그렇고, 배열은 포인터 일뿐 아니라 몇 가지 장점이 있습니다. (AB) 동기화 된 객체로 사용할 수 있습니다!

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top