Android все экземпляры класс

Классы и объекты

Java — это объектно-ориентированный язык, поэтому код в ваших программах будет состоять из объектов и классов.

Классы

Java позволяет создавать классы, которые представляют объекты из реального мира. Например, можно создать класс Car (автомобиль) или Animal (животное) и задать им различные свойства. Для класса Car логично создать такие свойства как двери, колёса, лобовое стекло и т.д. Имея класс Car, можно создать новые классы Легковушки, Грузовики, Автобусы, которые будут иметь все свойства класса Car, а также свои собственные свойства. У класса Animal соответственно можно задать свойства Лапы, Хвост, а затем создать наш любимый класс Cat, у которого будет ещё дополнительное свойство Усы. Иными словами, классы могут наследовать свойства от других классов. Родительский класс называется суперклассом. Внутри классов могут быть объявлены поля и методы.

Для объявления класса служит ключевое слово class. Вспомним стандартную строчку кода из Android-проекта:

Упрощённая общая форма для класса может иметь следующий вид:

В Java принято начинать имена класса с большой буквы. В классе могут быть несколько переменных и методов. Переменные, определённые внутри класса (не метода), называются переменными экземпляра или полями (fields). Код пишется внутри класса. Методы и переменные внутри класса являются членами класса.

Объекты

Новый объект (или экземпляр) создаётся из существующего класса при помощи ключевого слова new:

В большинстве случаев вы будете использовать такой способ. Пусть вас не удивляет, что приходится дважды использовать слово Cat, оно имеет разный смысл.

Слева от оператора присваивания = определяется имя переменной и его тип Cat. В правой части выражения происходит выделение памяти для нового экземпляра класса Cat и инициализируется экземпляр. Оператор присваивания присваивает переменной ссылку на только что созданный объект. Имена объектов не нужно начинать с большой буквы, как у класса. Так вы будете различать, где класс, а где экземпляр класса. Если имя экземпляра класса состоит из нескольких слов, то используется верблюжья нотация, когда все первые буквы слов, кроме первой, пишутся с большой — superBlackCat.

Если вы помните, при объявлении примитивных типов мы указывали нужный тип в самом начале.

Поэтому код Cat barsik также определяет его тип. Он не всегда может совпадать с именем класса.

В этом примере используется тип класса домашних любимцев Pet, а обращаемся к классу котов Cat.

Простой пример создания класса Box (коробка для кота):

При таком варианте Java автоматически присвоит переменным значения по умолчанию. Например, для int это будет значение 0. Но не всегда значения по умолчанию подойдут в вашем классе. Если вы создали переменную для описания количества лап у кота, то логично сразу присвоить значение 4. Поэтому считается хорошей практикой сразу присваивать нужные значения полям класса, не полагаясь на систему.

Вам нужно создать отдельный файл Box.java, в который следует вставить код, описанный выше. О том, как создавать новый файл для класса я не буду здесь расписывать.

Сам класс — это просто шаблон, заготовка. Чтобы ваше приложение могло использовать данный шаблон, нужно создать на его основе объект при помощи ключевого слова new:

Красивая получилась коробочка.

Объект catBox, объявленный в коде вашей программы, сразу займёт часть памяти на устройстве. При этом объект будет содержать собственные копии переменных экземпляра width, height, depth. Для доступа к этим переменным используется точка (.). Если мы хотим присвоить значение переменной width, то после создания объекта класса можете написать код:

Если мы хотим вычислить объём коробки, то нужно перемножить все значения размеров коробки:

Каждый объект содержит собственные копии переменных экземпляра. Вы можете создать несколько объектов на основе класса Box и присваивать разные значения для размеров коробки. При этом изменения переменных экземпляра одного объекта никак не влияют на переменные экземпляра другого объекта. Давайте объявим два объекта класса Box:

Читайте также:  Android смартфонов htc one

Когда мы используем конструкцию типа Box bigBox = new Box();, то в одной строке выполняем сразу два действия — объявляем переменную типа класса и резервируем память под объект. Можно разбить конструкцию на отдельные части:

Обычно такую конструкцию из двух строк кода не используют на практике, если нет особых причин.

Когда мы используем ключевое слово new и указываем имя класса, то после имени ставим круглые скобки, которые указывают на конструктор класса. О них поговорим позже.

Ключевое слово final

Поле может быть объявлено как final (финальное). Это позволяет предотвратить изменение содержимого переменной, по сути, это становится константой. Финальное поле должно быть инициализировано во время его первого объявления.

Теперь можно пользоваться переменной FILE_OPEN так, как если бы она была константой, без риска изменения их значений. Принято записывать имена заглавными буквами.

Кроме полей, final можно использовать для параметров метода (препятствует изменению в пределах метода) и у локальных переменных (препятствует присвоению ей значения более одного раза).

Также слово final можно применять к методам, чтобы предотвратить его переопределение.

Ещё один вариант использования ключевого слова final — предотвращение наследования класса. При этом неявно всего методы класса также становятся финальными. Поэтому нельзя одновременно объявить класс абстрактным и финальным, поскольку абстрактный класс является лишь шаблоном и только его подклассы реализуют методы.

Ключевое слово instanceof — Проверка принадлежности к классу

Иногда требуется проверить, к какому классу принадлежит объект. Это можно сделать при помощи ключевого слова instanceof. Это булев оператор, и выражение foo instanceof Foo истинно, если объект foo принадлежит классу Foo или его наследнику, или реализует интерфейс Foo (или, в общем виде, наследует класс, который реализует интерфейс, который наследует Foo).

Возьмём пример с рыбками, которые знакомы котам не понаслышке. Пусть у нас есть родительский класс Fish и у него есть унаследованные подклассы SaltwaterFish и FreshwaterFish. Мы можем протестировать, относится ли заданный объект к классу или подклассу по имени

Данная проверка удобна во многих случаях. В Android очень много классов, которые происходят от класса ViewTextView, CheckBox, Button, имеющие свои собственные наборы свойств. И если имеется метод с параметром View, то при помощи instanceof можно разделить логику кода:

import — Импорт класса

Оператор import сообщает компилятору Java, где найти классы, на которые ссылается код. Любой сложный объект использует другие объекты для выполнения тех или иных функций, и оператор импорта позволяет сообщить о них компилятору Java. Оператор импорта обычно выглядит так:

За ключевым словом import следуют класс, который нужно импортировать, и точка с запятой. Имя класса должно быть полным, то есть включать свой пакет. Чтобы импортировать все классы из пакета, после имени пакета можно поместить .*.

В Android Studio импорт класса происходит автоматически при наборе кода. Также это срабатывает и при вставке кода. Если имена классов совпадают, то студия может запросить помощь. Тогда вам нужно вручную указать нужное полное имя класса.

Импорт позволяет избежать долгого набора имени класса. Без импорта нам пришлось бы писать все классы в коде программы полностью.

Статический импорт

Существует ещё статический импорт, применяемый для импорта статических членов класса или интерфейса. Это позволяет сократить количество кода. Например, есть статические методы Math.pow(), Math.sqrt(). Для вычислений сложных формул с использованием математических методов, код становится перегружен. К примеру, вычислим гипотенузу.

В данном случае без указания класса не обойтись, так как методы статические. Чтобы не набирать имена классов, их можно импортировать следующим образом:

После импорта уже нет необходимости указывать имя класса.

Второй допустимый вариант, позволяющий сделать видимыми все статические методы класса:

В этом случае вам не нужно импортировать отдельные методы. Но такой подход в Android не рекомендуется, так как требует больше памяти.

Читайте также:  Спорт прогнозы для андроид

Класс Class

На первый взгляд, класс Class звучит как «масло масляное». Тем не менее, класс с таким именем существует и он очень полезен.

Программно получить имя класса

Иногда из программы нужно получить имя используемого класса. Для этого есть специальные методы getClass().getName() и другие родственные методы. Допустим, нам нужно узнать имя класса кнопки, на которую мы нажимаем в программе.

getSimpleName() возвращает только имя класса без пакета, другие методы вернут полное название.

Если нужно узнать имя класса активности, то достаточно кода:

Если вам известно имя класса, то можете получить сам класс:

Метод getSuperclass() возвращает имя суперкласса. Остальные несколько десятков методов не столь популярны.

Источник

Activity

Activity и жизненный цикл приложения

Ключевым компонентом для создания визуального интерфейса в приложении Android является activity (активность). Нередко activity ассоциируется с отдельным экраном или окном приложения, а переключение между окнами будет происходить как перемещение от одной activity к другой. Приложение может иметь одну или несколько activity. Например, при создании проекта с пустой Activity в проект по умолчанию добавляется один класс Activity — MainActivity, с которого и начинается работа приложения:

Все объекты activity представляют собой объекты класса android.app.Activity , которая содержит базовую функциональность для всех activity. В приложении из прошлой темы мы напрямую с этим классом не работали, а MainActivity наследовалась от класса AppCompatActivity . Однако сам класс AppCompatActivity, хоть и не напрямую, наследуется от базового класса Activity.

Жизненный цикл приложения

Все приложения Android имеют строго определенный системой жизненный цикл. При запуске пользователем приложения система дает этому приложению высокий приоритет. Каждое приложение запускается в виде отдельного процесса, что позволяет системе давать одним процессам более высокой приоритет, в отличие от других. Благодаря этому, например, при работе с одними приложениями Android позволяет не блокировать входящие звонки. После прекращения работы с приложением, система освобождает все связанные ресурсы и переводит приложение в разряд низкоприоритетного и закрывает его.

Все объекты activity, которые есть в приложении, управляются системой в виде стека activity, который называется back stack . При запуске новой activity она помещается поверх стека и выводится на экран устройства, пока не появится новая activity. Когда текущая activity заканчивает свою работу (например, пользователь уходит из приложения), то она удаляется из стека, и возобновляет работу та activity, которая ранее была второй в стеке.

После запуска activity проходит через ряд событий, которые обрабатываются системой и для обработки которых существует ряд обратных вызовов:

Схематично взаимосвязь между всеми этими обратными вызовами можно представить следующим образом

onCreate()

onCreate — первый метод, с которого начинается выполнение activity. В этом методе activity переходит в состояние Created. Этот метод обязательно должен быть определен в классе activity. В нем производится первоначальная настройка activity. В частности, создаются объекты визуального интерфейса. Этот метод получает объект Bundle , который содержит прежнее состояние activity, если оно было сохранено. Если activity заново создается, то данный объект имеет значение null. Если же activity уже ранее была создана, но находилась в приостановленном состоянии, то bundle содержит связанную с activity информацию.

После того, как метод onCreate() завершил выполнение, activity переходит в состояние Started , и и система вызывает метод onStart()

onStart

В методе onStart() осуществляется подготовка к выводу activity на экран устройства. Как правило, этот метод не требует переопределения, а всю работу производит встроенный код. После завершения работы метода activity отображается на экране, вызывается метод onResume , а activity переходит в состояние Resumed.

onResume

При вызове метода onResume activity переходит в состояние Resumed и отображается на экране устройства, и пользователь может с ней взаимодействовать. И собственно activity остается в этом состоянии, пока она не потеряет фокус, например, вследствии переключения на другую activity или просто из-за выключения экрана устройства.

Читайте также:  Как восстановить удаленные загрузки андроид

onPause

Если пользователь решит перейти к другой activity, то система вызывает метод onPause , а activity переходит в состояние Paused . В этом методе можно освобождать используемые ресурсы, приостанавливать процессы, например, воспроизведение аудио, анимаций, останавливать работу камеры (если она используется) и т.д., чтобы они меньше сказывались на производительность системы.

Но надо учитывать, что в этот состоянии activity по прежнему остается видимой на экране, и на работу данного метода отводится очень мало времени, поэтому не стоит здесь сохранять какие-то данные, особенно если при этом требуется обращение к сети, например, отправка данных по интернету, или обращение к базе данных — подобные действия лучше выполнять в методе onStop() .

После выполнения этого метода activity становится невидимой, не отображается на экране, но она все еще активна. И если пользователь решит вернуться к этой activity, то система вызовет снова метод onResume , и activity снова появится на экране.

Другой вариант работы может возникнуть, если вдруг система видит, что для работы активных приложений необходимо больше памяти. И система может сама завершить полностью работу activity, которая невидима и находится в фоне. Либо пользователь может нажать на кнопку Back (Назад). В этом случае у activity вызывается метод onStop .

onStop

В этом методе activity переходит в состояние Stopped. В этом состоянии activity полностью невидима. В методе onStop следует особождать используемые ресурсы, которые не нужны пользователю, когда он не взаимодействует с activity. Здесь также можно сохранять данные, например, в базу данных.

При этом во время состояния Stopped activity остается в памяти устройства, сохраняется состояние всех элементов интерфейса. К примеру, если в текстовое поле EditText был введен какой-то текст, то после возобновления работы activity и перехода ее в состояние Resumed мы вновь увидим в текстовом поле ранее введенный текст.

Если после вызова метода onStop пользователь решит вернуться к прежней activity, тогда система вызовет метод onRestart . Если же activity вовсе завершила свою работу, например, из-за закрытия приложения, то вызывается метод onDestroy() .

onDestroy

Ну и завершается работа activity вызовом метода onDestroy , который возникает либо, если система решит убить activity в силу конфигурационных причин (например, поворот экрана или при многоконном режиме), либо при вызове метода finish() .

Также следует отметить, что при изменении ориентации экрана система завершает activity и затем создает ее заново, вызывая метод onCreate .

В целом переход между состояниями activity можно выразить следующей схемой:

Расмотрим несколько ситуаций. Если мы работаем с Activity и затем переключаемся на другое приложение, либо нажимаем на кнопку Home, то у Activity вызывается следующая цепочка методов: onPause -> onStop . Activity оказывается в состоянии Stopped. Если пользователь решит вернуться к Activity, то вызывается следующая цепочка методов: onRestart -> onStart -> onResume .

Другая ситуация, если пользователь нажимает на кнопку Back (Назад), то вызывается следующая цепочка onPause -> onStop -> onDestroy . В результате Activity уничтожается. Если мы вдруг захотим вернуться к Activity через диспетчер задач или заново открыв приложение, то activity будет заново пересоздаваться через методы onCreate -> onStart -> onResume

Управление жизненным циклом

Мы можем управлять этими событиями жизненного цикла, переопределив соответствующие методы. Для этого возьмем из прошлой главы класс MainActivity и изменим его следующим образом:

Для логгирования событий здесь используется класс android.util.Log .

В данном случае обрабатываются все ключевые методы жизненного цикла. Вся обработка сведена к вызову метода Log.d() , в который передается TAG — случайное строковое значение и строка, которая выводится в консоли Logcat в нижней части Android Studio, выполняя роль отладочной информации. Если эта консоль по умолчанию скрыта, то мы можем перейти к ней через пункт меню View -> Tool Windows -> Logcat .

И при запуске приложения мы сможем увидеть в окне Logcat отладочную информацию, которая определяется в методах жизненного цикла activity:

Источник

Оцените статью