Sie sind auf Seite 1von 20

1) ANALYSE THE PROBLEM ENCOUNTERED

2) MEASURE
3)OPTIMIZE
Before you start optimizing, make sure you have a problem that you need to solve.
Make sure you can accurately measure your existing performance, or you won't be
able to measure the benefit of the alternatives you try.
The important step in developing applications that delight the user is to maximize your
applications performance
Users want application that use power sparingly, start up quickly and respond quickly
to user interaction.
Here are a few key points to implement:

Avoid Creating Unnecessary Objects


Object creation is never free. A generational garbage collector with per-thread allocation pools for
temporary objects can make allocation cheaper, but allocating memory is always more expensive than
not allocating memory.
As you allocate more objects in your app, you will force a periodic garbage collection, creating little
"hiccups" in the user experience. The concurrent garbage collector introduced in Android 2.3 helps, but
unnecessary work should always be avoided.
you should avoid creating object instances you don't need to. Some examples of things that can help:
Prefer Static Over Virtual
If you don't need to access an object's fields, make your method static. Invocations will be about
15%-20% faster. It's also good practice, because you can tell from the method signature that
calling the method can't alter the object's state.

Avoid Using Floating-Point


As a rule of thumb, floating-point is about 2x slower than integer on Android-powered devices.

Know and Use the Libraries


In addition to all the usual reasons to prefer library code over rolling your own, bear in mind that
the system is at liberty to replace calls to library methods with hand-coded assembler, which may
be better than the best code the JIT can produce for the equivalent Java. The typical example here
is String.indexOf() and related APIs, which Dalvik replaces with an inlined intrinsic. Similarly, the
System.arraycopy() method is about 9x faster than a hand-coded loop on a Nexus One with the JIT.
Optimizing Layout Hierarchies
It is a common misconception that using the basic layout structures leads to the most efficient
layouts. However, each widget and layout you add to your application requires initialization, layout,
and drawing. For example, using nested instances of LinearLayout can lead to an excessively deep
view hierarchy. Furthermore, nesting several instances of LinearLayout that use the layout_weight
parameter can be especially expensive as each child needs to be measured twice. This is
particularly important when the layout is inflated repeatedly, such as when used in a ListView or
GridView.

The Android SDK tools include a tool called Hierarchy Viewer that allows you to analyze your
layout while your application is running. Using this tool helps you discover bottlenecks in the
layout performance.

Use Lint tool on your layout files to search for possible view hierarchy optimizations.
Create a Re-usable Layout using <include > tag and <merge> tag
Although Android offers a variety of widgets to provide small and re-usable interactive
elements, you might also need to re-use larger components that require a special layout. To
efficiently re-use complete layouts, you can use the <include/> and <merge/> tags to embed
another layout inside the current layout.
Reusing layouts is particularly powerful as it allows you create reusable complex layouts. For
example, a yes/no button panel, or custom progress bar with description text. It also means that
any elements of your application that are common across multiple layouts can be extracted,
managed separately, then included in each layout. So while you can create individual UI
components by writing a custom View, you can do it even more easily by re-using a layout file

Loading Views On Demand

Sometimes your layout might require complex views that are rarely used. Whether they are item
details, progress indicators, or undo messages, you can reduce memory usage and speed up
rendering by loading the views only when they are needed
Optimizing Battery Life
Monitoring the Battery level and charging state:
When you're altering the frequency of your background updates to reduce the
effect of those updates on battery life, checking the current battery level and charging
state is a good place to start.
The battery-life impact of performing application updates depends on the battery level
and charging state of the device. The impact of performing updates while the device is
charging over AC is negligible, so in most cases you can maximize your refresh rate
whenever the device is connected to a wall charger. Conversely, if the device is
discharging, reducing your update rate helps prolong the battery life.
Similarly, you can check the battery charge level, potentially reducing the frequency of
or even stoppingyour updates when the battery charge is nearly exhausted
Determining and Monitoring the Docking state and Type
Android devices can be docked into several different kinds of docks. These
include car or home docks and digital versus analog docks. The dock-state is
typically closely linked to the charging state as many docks provide power to
docked devices.
How the dock-state of the phone affects your update rate depends on your app. You
may choose to increase the update frequency of a sports center app when it's in the
desktop dock, or disable your updates completely if the device is car docked.
Conversely, you may choose to maximize your updates while car docked if your
background service is updating traffic conditions.
The dock state is also broadcast as a sticky Intent, allowing you to query if the device
is docked or not, and if so, in which kind of dock
Determining and Monitoring the connectivity status
Some of the most common uses for repeating alarms and background
services is to schedule regular updates of application data from Internet
resources, cache data, or execute long running downloads. But if you aren't
connected to the Internet, or the connection is too slow to complete your download,
why bother waking the device to schedule the update at all?
You can use the ConnectivityManager to check that you're actually
connected to the Internet, and if so, what type of connection is in place
Manipulating Broadcast Receivers on Demand
The simplest way to monitor device state changes is to create a
BroadcastReceiver for each state you're monitoring and register each of them
in your application manifest. Then within each of these receivers you simply
reschedule your recurring alarms based on the current device state.
A better approach is to disable or enable the broadcast receivers at runtime.
That way you can use the receivers you declared in the manifest as passive
alarms that are triggered by system events only when necessary.
Keeping Your App Responsive
It's possible to write code that wins every performance test in the world, but still feels sluggish,
hang or freeze for significant periods, or take too long to process input. The worst thing that can
happen to your app's responsiveness is an "Application Not Responding" (ANR) dialog.

In any situation in which your app performs a potentially lengthy operation, you should not
perform the work on the UI thread, but instead create a worker thread and do most of the work
there. This keeps the UI thread (which drives the user interface event loop) running and
prevents the system from concluding that your code has frozen. Because such threading usually
is accomplished at the class level, you can think of responsiveness as a class problem.
(Compare this with basic code performance, which is a method-level concern.)
In Android, application responsiveness is monitored by the Activity Manager and Window
Manager system services. Android will display the ANR dialog for a particular application
when it detects one of the following conditions:
No response to an input event (such as key press or screen touch events) within 5 seconds.
A BroadcastReceiver hasn't finished executing within 10 seconds.
Any method that runs in the UI thread should do as little work as possible on that
thread. In particular, activities should do as little as possible to set up in key life-
cycle methods such as onCreate() and onResume()
Potentially long running operations such as network or database operations, or
computationally expensive calculations such as resizing bitmaps should be done in
a worker thread (or in the case of databases operations, via an asynchronous
request).
The most effective way to create a worker thread for longer operations is with the
AsyncTask class. Simply extend AsyncTask and implement the doInBackground()
method to perform the work. To post progress changes to the user, you can call
publishProgress(), which invokes the onProgressUpdate() callback method. From
your implementation of onProgressUpdate() (which runs on the UI thread), you can
notify the user.
Permission requests protect sensitive information
available from a device and should only be used
when access to information is necessary for the
functioning of your app.
#1: Only use the permissions necessary for your app to work. Depending on how you
are using the permissions, there may be another way to do what you need (system
intents, identifiers, backgrounding for phone calls) without relying on access to
sensitive information.
#2: Pay attention to permissions required by libraries. When you include a library,
you also inherit its permission requirements. You should be aware of what you're
including, the permissions they require, and what those permissions are used for.
#3: Be transparent. When you make a permissions request, be clear about what youre
accessing, and why, so users can make informed decisions. Make this information
available alongside the permission request including install, runtime, or update
permission dialogues.
#4: Make system accesses explicit. Providing continuous indications when you access
sensitive capabilities (for example, the camera or microphone) makes it clear to users
when youre collecting data and avoids the perception that you're collecting data
surreptitious
Testing your app is an integral part of the app development process. Testing allows
you to verify the correctness, functional behavior, and usability of your app before
it is released publicly.

Android tests are based on JUnit, and you can run them either as local unit tests on
the JVM or as instrumented tests on an Android device
JUnit is a simple framework to write repeatable tests. It is an instance of the xUnit
architecture for unit testing frameworks.
When using Android Studio to write any of your tests, your test code must go into one of two
different code directories (source sets). For each module in your project, Android Studio includes
both source sets, corresponding to the following test types:

UNIT TESTS
Local unit tests
Located at module-name/src/test/java/.
These tests run on the local JVM and do not have access to functional Android framework APIs.
Unit tests that run locally on the Java Virtual Machine (JVM). Use these tests to minimize execution time
when your tests have no Android framework dependencies or when you can mock the Android framework
dependencies.
Instrumented tests
Located at module-name/src/androidTest/java/.
These are all tests that must run on an Android hardware device or an Android emulator.
These tests have access to Instrumentation information, such as the Context of the app you are testing. Use
these tests when your tests have Android dependencies that mock objects cannot satisfy.
INTEGRATION TEST
Components within your app only
This type of test verifies that the target app behaves as expected when a user performs a specific
action or enters a specific input in its activities. For example, it allows you to check that the target
app returns the correct UI output in response to user interactions in the apps activities. UI testing
frameworks like Espresso allow you to programmatically simulate user actions and test complex
intra-app user interactions.

Cross-app Components
This type of test verifies the correct behavior of interactions between different user apps or
between user apps and system apps. For example, you might want to test that your app behaves
correctly when the user performs an action in the Android Settings menu. UI testing frameworks
that support cross-app interactions, such as UI Automator, allow you to create tests for such
scenarios
The Android SDK includes two tools for functional-level app testing:
Monkey
This is a command-line tool that sends pseudo-random streams of keystrokes, touches,
and gestures to a device. You run it with the Android Debug Bridge (adb) tool, and use it
to stress-test your app, report back errors any that are encountered, or repeat a stream of
events by running the tool multiple times with the same random number seed.
monkeyrunner
This tool is an API and execution environment for test programs written in Python. The API
includes functions for connecting to a device, installing and uninstalling packages, taking
screenshots, comparing two images, and running a test package against an app. Using the
API, you can write a wide range of large, powerful, and complex tests. You run programs
that use the API with the monkeyrunner command-line tool

Das könnte Ihnen auch gefallen