Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > Java: Общие вопросы > Передача укзателя на простую переменную в функцию


Автор: Santa777 23.12.2009, 15:36
Здравствуйте,

  Перерыл интернет, но так до конца и нет понял можно ли все таки в Java передать в фукнцию указатель на простую переменную.
  В C++ это выглядело бы так:
Код

  class ClassA 
  {
      int i
  }

  void Inc( int* i )
  {
       (*i)++;
  }

  void main()
  {

      ClassA c;
      c.i = 1;

      Inc( &c.i );
  
      //i стало 2
  }

  Класс объявлен, чтобы показать, что переменная уже существует как просто переменная внутри класса. Ее нельзя хитро объявить саму по себе.
  
  Знатоки, подскажите, пожалуйста, как это может выглядеть в Java?

Автор: jk1 23.12.2009, 15:54
Насколько я знаю, такой возможности нет. В таких случаях в Java используются http://java.sun.com/docs/books/tutorial/java/data/numberclasses.html примитивных типов.

Автор: LSD 23.12.2009, 16:00
В данном случае, скорее http://commons.apache.org/lang/api-2.4/org/apache/commons/lang/mutable/MutableInt.html, потому как стандартная обертка immutable.

Автор: jk1 23.12.2009, 16:09
Хм. Я был уверен, что для классов-оберток предпочтительна именно immutable-форма. В таком случае ссылка из класса-обертки на фактическое значение потенциально неспособна стать ссылкой из старого поколения в новое, усложнив работу сборщику мусора. Или я не прав?

Вопрос снят. что-то я тормознул, с immutable действительно ничего не выйдет 

Автор: Santa777 23.12.2009, 16:14
  Там именно что все уже определено - int и все.
  Как понял, прав jk1, с примитивными типами такого нельзя.
  Спасибо!

   Подумал на эту тему: вот изначально вопрос возник из-за того, что
мне надо было поменять значения 5-ти переменных подряд т.е.:

    a = 1;
    b = 2;

    int xchg;
    xchg = a;
    a = b;
    b = xchg;

  И так 5 раз.
  Неужели в Java для таких случаев ничего не предусмотрено?

Автор: serger 23.12.2009, 16:19
Насколько помню, эти тонкости разобраны в книге Эккеля "Философия Java". Достать её не трудно.

Добавлено через 1 минуту и 4 секунды
Цитата(Santa777 @  23.12.2009,  16:14 Найти цитируемый пост)
Неужели в Java для таких случаев ничего не предусмотрено?

Нет, а что бы хотелось?

Автор: Santa777 23.12.2009, 16:55
Цитата

Цитата(Santa777 @  23.12.2009,  16:14 Найти цитируемый пост)
Неужели в Java для таких случаев ничего не предусмотрено?

Нет, а что бы хотелось?


Чего-нибудь типа C-шного же #define:

#define xchg(a, b) {int xchg; xchg = a; a = b; b = xchg;}

Просто, так сказать, и сердито.
Или они есть где-нибудь?

Автор: Skynin 23.12.2009, 17:09
В Java нет указателей на типы-значения. Только ссылки на объекты.

Поэтому либо использовать обертки, либо

Код

public class ABvalue {
public int a, b;

public ABvalue(int pA, int pB) {
a = pA; b = pB;
}

...

... ... swapAB(ABvalue pAB) {
int tmpI = pAB.a;
pAB.a = pAB.b;
pAB.b = tmpI;
}

...

ABvalue tttAB = new ABvalue(1,2);

...

xxxx.swapAB(tttAB);



то есть создание аналога структуры и работа с ней.

Цитата

Чего-нибудь типа C-шного же #define:

В Java нет препроцессора. И много чего нет, что есть в С++, перечислять утомительно.
Лучше прочтите какую-нить книгу по Java. Рекомендую "Философия Java" Б. Эккеля

Автор: COVD 23.12.2009, 17:23
Цитата

Нет, а что бы хотелось?


Хотелось бы на всех иностранных языках говорить русскими фразами. И только слова подставлять из соответствующего словаря. И чтобы понимали. smile   

Автор: math64 24.12.2009, 09:16
Приведённые обертки не изменяют поле класса, поэтому не годятся. Нужно что-то вроде этого:
Код

public class ClassA {
  public interface IntRef {
     int get();
     void set(int v);
  }
  private int a, b, c;
  IntRef A = new IntRef() { public int get() { return a; } public void set(int v) { a = v; } };
  IntRef B = new IntRef() { public int get() { return b; } public void set(int v) { b = v; } };
  IntRef C = new IntRef() { public int get() { return c; } public void set(int v) { c = v; } };
  public void swap(IntRef x, IntRef y) {
     int temp = x.get(); x.set(y.get()); y.set(temp);
  }
  public void foo() {
    swap(A, B);
    swap(B, C);
  }
}

Автор: serger 24.12.2009, 13:32
Цитата(Santa777 @  23.12.2009,  16:55 Найти цитируемый пост)
Чего-нибудь типа C-шного же #define:

#define xchg(a, b) {int xchg; xchg = a; a = b; b = xchg;}


Тогда уж проще :
Код

def a=1
def b=2
println "$a,$b"
(a,b) = [b,a]
println "$a,$b"


Посмотрите groovy.
http://groovy.codehaus.org/Statements

Автор: Zefick 25.12.2009, 05:50
Странно, что ещё никто не предложил оборачивать переменную в массив, а ведь это часто используется.
Код

class A {
    void Inc(int i[]){
        i[0]++;
    }

    public static void main(String[] args){
        int i = 1;
        Inc(new int[] {i});
    }
}

Автор: math64 25.12.2009, 08:53
Цитата(Zefick @  25.12.2009,  05:50 Найти цитируемый пост)
Странно, что ещё никто не предложил оборачивать переменную в массив, а ведь это часто используется.

Тот же недостаток, что и у обычных обёрток - результат остаётся в массиве и после вызова функции его нужно вернуть в поле класса.
Хотя я им тоже часто пользуюсь.

Автор: LSD 25.12.2009, 17:09
Цитата(math64 @  24.12.2009,  09:16 Найти цитируемый пост)
Приведённые обертки не изменяют поле класса, поэтому не годятся. Нужно что-то вроде этого:

А поле класса объявить как MutableInt, не?

Автор: math64 28.12.2009, 10:19
Цитата(LSD @  25.12.2009,  17:09 Найти цитируемый пост)
А поле класса объявить как MutableInt, не?

Можно и так (или объявить поле класса как int[1]), в зависимости от требований к скорости и размеру кода.

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)