我一直在研究在创建视图时防止上下文/活动内存泄漏的最佳实践,而且我似乎无法找到关于类中静态字段允许或不允许的内容的明确答案.
假设我有这种形式的代码:
public class MyOuterClass extends Activity{
private MyInnerClass;
MyInnerClass = (MyInnerClass) findViewById(<XML call here>);
MyInnerClass.myXInt = 3;
// onCreate(), onResume(), etc.
public static class MyInnerClass extends SurfaceView implements Runnable{
// Safe variables?
private static int myXInt, myYInt;
private static boolean myBoolean;
// Potentially safe?
private static Canvas myCanvas;
// Definitely bad.
private static Context myContext;
public MyInnerClass(Context context){
myContext = context; // This is bad.
}
}
}
Run Code Online (Sandbox Code Playgroud)
关于JVM实际上认为MyInnerClass的ClassLoader是什么,我有点困惑.从技术上讲,由于它是一个SurfaceView对象,一旦应用程序实例化MyInnerClass一次(在View首次膨胀时发生),静态变量似乎应该总是存在,然后保持在那里直到应用程序本身终止.如果是这种情况,是什么阻止Bitmaps和Canvas对象保持打开并填满堆?
我曾经反复重复的唯一一句话就是你不能像我在构造函数中看到的那样泄漏静态上下文,但它永远不会超越它.这真的是你唯一不能做的事情吗?
memory android memory-leaks android-context android-activity
我开始使用a ContextThemeWrapper来动态地应用一个样式ImageButton; 基于对我的另一个问题的回答,以及对其他类似 问题的回答.
ContextThemeWrapper wrapper = new ContextThemeWrapper(getContext(), mStyleRes);
mImageButton = new AppCompatImageButton(wrapper, null, 0);
Run Code Online (Sandbox Code Playgroud)
但最近一个lint错误开始出现在ContextThemeWrapper构造函数上:
ContextThemeWrapper只能从同一个库组中调用(groupId = com.android.support)
我注意到标有@RestrictTo(LIBRARY_GROUP)注释的类,这会导致lint错误出现.但是我找不到任何关于它为什么仅限于com.android.support图书馆组的信息.
据我所知,这是以View编程方式应用样式,主题或主题叠加的唯一方法; 除了将默认样式属性设置为构造函数中的第三个参数之外.所以我想知道为什么它的使用会受到限制; 在支持库之外使用类有什么问题吗?可能会有我不知道的副作用吗?
我遇到的唯一类似的问题是关于(现在已修复)的错误; 导致此lint错误显示在onCreate子类的方法上AppCompatActivity.我认为这不是一个错误,而是一个故意的限制; 我想知道背后的推理.
我应该注意; 这个限制(截至目前)实际上似乎对使用a的代码没有影响ContextThemeWrapper.它编译并运行良好,并按照我的预期工作.
android syntax-error android-context android-lint android-support-library
这可能是一个简单的问题,但我只是想确保我是对的.
在我的Android应用程序中,我有一个使用的构造函数:
activity.getApplicationContext()
Run Code Online (Sandbox Code Playgroud)
活动作为参数传递给构造函数.
问题是我从服务中调用此类.如果我创建第二个构造函数接受服务作为参数并使用service.getApplicationContext?我会获得相同的应用程序上下文吗?
我必须构建一个使用sqlite的应用程序.现在我想写单元测试.这些单元测试应该测试我的课程SQLiteBridge.SQLiteBridge为每个子类Model提供DAO.
现在我遇到了一个问题,我需要一个上下文来创建我的SQLiteBridge.SQLiteBridge在系统上创建和处理SQLite数据库..
从哪里获取Context-Object?
我的设置就像在这里(所以我使用的是Junit4 [感谢上帝]):http: //tools.android.com/tech-docs/unit-testing-support
编辑:我希望有一种方式像旧AndroidTestCase的扩展而不会失去Junit4.:)
我有以下代码
public abstract class BaseAdapter<T, V extends BaseAdapter.ViewHolder> extends ArrayAdapter<T> {
public BaseAdapter(Context context, int resource, Collection<T> collection) {
// typical constructor logic
}
// some other custom defined methods
public static class ViewHolder {
// custom defined logic
}
}
public class ModelAdapter extends BaseAdapter<Model, ModelAdapter.ModelViewHolder> {
public ModelAdapter(Context context, int resource, Collection<Model> collection) {
super(context, resource, collection);
// typical constructor logic
}
public static class ModelViewHolder extends ViewHolder {
// custom defined logic
}
}
Run Code Online (Sandbox Code Playgroud)
BaseAdapter和ModelAdapter位于单独的文件中.问题是我在尝试定义ModelAdapter时遇到编译错误:在当前上下文中无法访问 ModelViewHolder …
我正在使用Context来访问WifiManager和BluetoothManager等系统级服务.如何使用Mockito模拟这个getApplicationContext()?
将Context传递给构造函数并将其保存为私有变量供内部使用是不好的做法吗?另一种选择是将Context作为参数传递给需要它的方法.
哪个更好?我有一种感觉,传递给构造函数可能会导致内存泄漏意外.
更新2012年2月13日:接受了一个答案,解释说这种行为是一个错误,并指出它似乎已经比v 1.6更好地消失在模拟器上,这使得它对我们大多数人来说都不是问题.解决方法只是循环/休眠,直到getContext().getApplicationContext()返回非null.结束更新
按照android.app.Application的javadoc,我定义了一个单例(称为数据库)我所有的活动中访问了状态和持久性数据,并Database.getDatabase(上下文)通过Context.getApplicationContext获取应用程序上下文().当活动通过自己getDatabase(上下文)这个设置像宣传的那样,但是当我从AndroidTestCase的getApplicationContext(运行单元测试)经常呼叫返回null,虽然较长的测试中,更频繁地返回一个非空值.
以下代码在AndroidTestCase中重现null - 单例不是演示所必需的.
首先,要记录app-instantiation消息,在测试中的应用程序中我定义了MyApp并将其添加到清单中.
public class MyApplication extends Application {
@Override
public void onCreate() {
super.onCreate();
Log.i("MYAPP", "this=" + this);
Log.i("MYAPP", "getAppCtx()=" + getApplicationContext());
}
}
Run Code Online (Sandbox Code Playgroud)
接下来,我定义了一个测试用例,用于报告AndroidTestCase.getContext()4次,由一些睡眠和一个getSharedPreferences()调用分开:
public class DatabaseTest extends AndroidTestCase {
public void test_exploreContext() {
exploreContexts("XPLORE1");
getContext().getSharedPreferences("foo", Context.MODE_PRIVATE);
exploreContexts("XPLORE2");
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
exploreContexts("XPLORE3");
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
exploreContexts("XPLORE4");
}
public void exploreContexts(String …Run Code Online (Sandbox Code Playgroud) 我有一个我正在尝试启动的IntentService.当我这样做时,它会吐出这个:
java.lang.RuntimeException: Unable to start service com.pec.testapp.service.NewsService@406bd940 with Intent { cmp=com.pec.testapp/.service.NewsService }: java.lang.NullPointerException
at android.app.ActivityThread.handleServiceArgs(ActivityThread.java:2173)
... (omitted for brevity)
Caused by: java.lang.NullPointerException
at android.app.IntentService.onStart(IntentService.java:110)
at android.app.IntentService.onStartCommand(IntentService.java:118)
at android.app.ActivityThread.handleServiceArgs(ActivityThread.java:2160)
... 10 more
Run Code Online (Sandbox Code Playgroud)
我已经搜索了这个,并查看了尽可能多的类似StackOverflow问题.然而,有一些微妙的差异,我无法解决.首先,异常中没有引用任何类.其次,通过更改上下文或双重检查来确定类似的问题,以确保它不为空.
我有代码来检查是不是这样:
public Context context;
@Override
public void onCreate(Bundle savedInstanceState){
super.onCreate(savedInstanceState);
context = getApplicationContext();
if(context == null)
Log.d("PECAPP","Context is null");
setContentView(R.layout.news_layout);
...Omit button code...
button.setOnClickListener(new OnClickListener(){
@Override
public void onClick(View view){
Intent i = new Intent(context, NewsService.class); // also tried NewsActivity.this
if( i != null) // I know that …Run Code Online (Sandbox Code Playgroud) 有没有办法在Android中动态查看特定于应用程序的缓存?我正在将图像保存到缓存(/ data/data/my_app_package/cache),我99%肯定他们在那里保存,但不确定他们待在一起多久.
当我使用Eclipse中的DDMS文件资源管理器查看缓存时,它始终为空.我也尝试在ADB中检查适当的缓存目录,并且它总是空的.
有什么建议?
android ×10
android-context ×10
java ×2
memory-leaks ×2
service ×2
unit-testing ×2
android-lint ×1
android-wifi ×1
bluetooth ×1
caching ×1
generics ×1
image ×1
junit ×1
memory ×1
mockito ×1
scope ×1
sqlite ×1
syntax-error ×1