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


Автор: oson 27.6.2008, 22:55
Вот например есть класс
Код



public class State
{
    private static Integer val;
 
    public static Integer val()
    {
        return val;
    }

    public void setVal(Integer val)
    {
        State.val = val;
    }


}


и в Spring файлике я его инициализирую
Код

<bean id="state" class="util.State">
        <property name="val" value="0"/>
    </bean>


и где то я использую этот бин
Код

 Integer smth = State.val();



Метод static Integer val() получается имеет такое имя как статическая переменная в классе State. Можно было бы сделать static Integer getVal() - но меня смущает, что getVal() - это зарезервированное имя как бы для НЕстатических методов.
Как правильно -
1-делать метод статический с таким же именем как переменная val()
или
2 - делать метод статический getVal() ?

Автор: Kangaroo 28.6.2008, 00:13
Цитата(oson @  27.6.2008,  22:55 Найти цитируемый пост)
getVal() - это зарезервированное имя как бы для НЕстатических методов.

Никто его не резервировал, поэтому getVal() - лучший вариант.

Но смысла в классе с статическим гетом и нестатическим сетом я не вижу smile

Автор: ecologist 28.6.2008, 00:19
Тем более, что по умолчанию Спринг создает синглтоны - т.е. как раз один бин и будет создан. Вообщем-то не не вижу смысла в статике вообще. В данном конкретном случае.

Автор: oson 28.6.2008, 15:01
Если я делаю   Integer val не статик -то спринг ее вообще не инициализирует :(
Вот я пробую со статиком мудрить.
Да и когда мне надо получить эту самую Val где-то в коде - (это вроде глобальной переменной для всего приложения, которую я перед стартом приложения установил в нужное мне значение в конф файле спринга) - то не хочется каждый раз создавать новый обьект
Код

new State().getVal();
 

Автор: powerOn 28.6.2008, 17:57
Цитата(oson @  28.6.2008,  16:01 Найти цитируемый пост)
Если я делаю   Integer val не статик -то спринг ее вообще не инициализирует :(

Значит ты что то не так делаешь. Все он должен инициализировать. 

Автор: oson 29.6.2008, 10:52
не совсем понятно следующее
Spring по умолчанию делает синглетон.
Но я когда хочу воспользоваться этим синглетоном - ну то есть тем самым единственным инстанцом который сгенерировал Спринг - то где я его должен взять?
Я же все равно делаю
Код

Integer smth = new State.getVal();

то есть создаю новый обьект коласса State.
Если же я напишу что-нибудь типа 
Код

  public class State
{
    private State instance;
    public static State instance()
    {
        if(instance == null) 
        {
           instance = new State();
        }
        return instance;
     }
}

то я во-первых буду дублировать ту работу наверное чтоделает Спринг когда создает единственный обьект класса
а во-вторых это будут 2 разных обьекта - тот что проинициализирует Спринг исходя из его xml файла, и тот что я создам вот тут в коде сам.

Автор: oson 29.6.2008, 11:09
А иначе получается ошибка.
Спринг создает инстанц класса State  и устанавливает переменную val например в состояние 1.
Но когда я в другом месте кода хочу прочитать эту переменную val и делаю 
Код

Integer smth = new State().getVal();

то обьект этот же сосвсем другой в отличие от созданного Спрингом и переменная val там null.


Автор: gosnis 29.6.2008, 12:46
Я не специалист в Спринге, но, по моему, Вы не совсем понимаете синглтон. Вся фишка синглтона в том, что его конструктор приватный. Вы не можете его запустить. Инстанс синглтона получается доступом к статической функции. Что то типа Singleton s = Singleton.getInstance().
Так что меня сильно смущает Ваше new State()

Автор: Greg 29.6.2008, 14:03
Цитата(oson @  29.6.2008,  10:52 Найти цитируемый пост)
Но я когда хочу воспользоваться этим синглетоном - ну то есть тем самым единственным инстанцом который сгенерировал Спринг - то где я его должен взять?

С помощью
Код

org.springframework.beans.factory.BeanFactory.getBean(String name) 

и его перегруженных аналогов. 
    Идея заключается в том, что бы передать управление процессом конструирования и инициализации объектов фреймворку. Соответственно приложение априори ничего не знает о том, как создать (проинициализировать) объект, хотя ему предоставляется возможность получить экземпляр(ы) требуемого объекта через фабричный метод getBean().

Автор: oson 29.6.2008, 20:19
Это 

Код

State state =  (State)org.springframework.beans.factory.BeanFactory.getBean("statebean"); 

равносильно тому, чтоб прописать оба класса в конф файле спринга? Я имею ввиду вот так
Код



<beans>
    <bean id="function" class="my.Functions">
        <property name="state" ref="statebean"/>
    </bean>

     <bean id="statebean" class="my.State" singleton="true">
        <property name="val" value="1"/>
    </bean>
</beans>

public class Function
{
  private State state;
  public void setState()
  {
    this.state = state;
  }
}

Автор: Greg 30.6.2008, 00:08
Мухи и котлеты не путать. Прописать оба класса в конф файле спринга - значит указать ему как ты хочешь, что бы он создавал и инициализировал объекты этих классов. ВСЕ. После того, как приложение запустилось, в какой-то момент, спринг создает экземпляры объявленных в конфигурации классов и помещает их в свой контекст. 
Код

State state =  (State)org.springframework.beans.factory.BeanFactory.getBean("statebean"); 
 используется для получения ранее созданного экземпляра. По умолчанию, на одно объявление класса создается один его экземпляр. Все последующие вызовы этого же метода будут возвращать ссылку на тот же экземпляр.

Автор: AntonSaburov 30.6.2008, 13:21
Цитата(oson @  29.6.2008,  11:09 Найти цитируемый пост)
Integer smth = new State().getVal();

В добавок в предыдущему посту - эта строка уже не подпадает под управление Spring - это ты сам создаешь такой объект. И сам должен его инициализировать. 
А то, что создал Spring надо брать из его же контекста и тольок оттуда. И вот именно в этом контексте будет существовать один экземпляр.

Автор: oson 30.6.2008, 15:18
Так как правильно брать из его же контекста - прописав в файле спринга оба бина или используя BeanFactory.getBean("statebean")?

Автор: ivg 30.6.2008, 15:45
Цитата(oson @  30.6.2008,  18:18 Найти цитируемый пост)
Так как правильно брать из его же контекста - прописав в файле спринга оба бина или используя BeanFactory.getBean("statebean")?

С точки зрения Spring'а первый вариант, для этого он (Spring) и придуман.
Кроме того, по моему, второй вариант связан с определёнными сложностями - спринговый контекст, должен быть сконфигурирован определённым образом, чтобы в коде получить нужную реализацию интерфейса BeanFactory, и это не для каждого подойдёт. Возможно ошибаюсь, поправьте, кто спец по Спрингу.

Автор: Kangaroo 30.6.2008, 18:17
Цитата(oson @  30.6.2008,  15:18 Найти цитируемый пост)
Так как правильно брать из его же контекста - прописав в файле спринга оба бина или используя BeanFactory.getBean("statebean")? 

Конечно первый вариант. Так ты уберешь зависимость от спринга (твои классы вообще не будут знать о его существовании) и бин фактори там не к чему.

Кстати, BeanFactory это интерфейс и статического метода getBean() у него никак не может быть.

Автор: Greg 30.6.2008, 19:31
Цитата(oson @  30.6.2008,  15:18 Найти цитируемый пост)
Так как правильно брать из его же контекста - прописав в файле спринга оба бина или используя BeanFactory.getBean("statebean")? 
Грубо говоря, контекст - это хранилище. Хранилище, как таковое, имеет смысл только тогда, когда к нему можно обратиться (положить/достать объект). Каким образом ? В web приложении, на основе Java Servlets контекст в терминологии Spring - это экземпляр типа WebApplicationContext и хранится он в ServletContext, как значение аттрибута. BeanFactory - один из его прародительских интерфейсов, он инкапсулирует в себе информацию о форме хранилища, т.е. о том, что и как можно оттуда получить. Теперь, думаю, ясно, что метод getBean - это способ получения необходимого объекта из контекста ?

Цитата(Kangaroo @  30.6.2008,  18:17 Найти цитируемый пост)
Так ты уберешь зависимость от спринга (твои классы вообще не будут знать о его существовании) и бин фактори там не к чему.
 Говоря правильно, это звучало бы по другому: так ты используешь механизм Dependency Injection, который предоставляется Spring из коробки, тем самым очистив код своего приложения от низкоуровневых вызовов. Хотя иногда, все же может понадобиться обратиться к контексту на прямую из кода.


Цитата(Kangaroo @  30.6.2008,  18:17 Найти цитируемый пост)

Кстати, BeanFactory это интерфейс и статического метода getBean() у него никак не может быть. 

Конечно, метод не статический - это недоразумения сокращенной нотации. Поскольку она применяется довольно часто, я думал, что меня поймут правильно.

Автор: fixxer 30.6.2008, 22:49
Цитата(Greg @ 30.6.2008,  19:31)
Цитата(Kangaroo @  30.6.2008,  18:17 Найти цитируемый пост)

Кстати, BeanFactory это интерфейс и статического метода getBean() у него никак не может быть. 

Конечно, метод не статический - это недоразумения сокращенной нотации. Поскольку она применяется довольно часто, я думал, что меня поймут правильно.

Чтобы подчеркнуть, что речь идет о методе экземпляра обычно пишут так: BeanFactory#getBean()

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