Android: Strange NullPointerException while using SharedPreferences
我正在尝试创建一个静态包装类来处理我的应用程序的共享首选项。我创建了一个助手类
1 2 | MyHelper.Setting.saveBoolean("auto_start", true); MyHelper.Setting.grabBoolean("auto_start"); |
这是我的助手课程。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 | public class MyHelper{ public static class Setting extends android.app.Application { private static Context currentContext; private static SharedPreferences preferences; private static Editor updater; @Override public void onCreate(){ super.onCreate(); currentContext = this; preferences = PreferenceManager .getDefaultSharedPreferences(currentContext); updater = preferences.edit(); } public static boolean grabBoolean(String key) { return preferences.getBoolean(key, false); } public static void saveBoolean(String key, boolean value) { preferences.putBoolean(key, value).commit(); } } /* * Some other nested classes here... */ } |
我用
通过扩展
我已经阅读了Android开发者的参考资料和其他几个问题,但没有一个能解决这个问题。对于这个问题的任何指导、建议或确切的解决方案,我们都将非常感谢。
更新:logcat错误
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 | 12-04 12:14:47.467: E/AndroidRuntime(514): FATAL EXCEPTION: main 12-04 12:14:47.467: E/AndroidRuntime(514): java.lang.RuntimeException: Unable to start activity ComponentInfo{np.com.njs.statusinformer/np.com.njs.statusinformer.Setup}: java.lang.NullPointerException 12-04 12:14:47.467: E/AndroidRuntime(514): at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:1647) 12-04 12:14:47.467: E/AndroidRuntime(514): at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:1663) 12-04 12:14:47.467: E/AndroidRuntime(514): at android.app.ActivityThread.access$1500(ActivityThread.java:117) 12-04 12:14:47.467: E/AndroidRuntime(514): at android.app.ActivityThread$H.handleMessage(ActivityThread.java:931) 12-04 12:14:47.467: E/AndroidRuntime(514): at android.os.Handler.dispatchMessage(Handler.java:99) 12-04 12:14:47.467: E/AndroidRuntime(514): at android.os.Looper.loop(Looper.java:123) 12-04 12:14:47.467: E/AndroidRuntime(514): at android.app.ActivityThread.main(ActivityThread.java:3683) 12-04 12:14:47.467: E/AndroidRuntime(514): at java.lang.reflect.Method.invokeNative(Native Method) 12-04 12:14:47.467: E/AndroidRuntime(514): at java.lang.reflect.Method.invoke(Method.java:507) 12-04 12:14:47.467: E/AndroidRuntime(514): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:839) 12-04 12:14:47.467: E/AndroidRuntime(514): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:597) 12-04 12:14:47.467: E/AndroidRuntime(514): at dalvik.system.NativeStart.main(Native Method) 12-04 12:14:47.467: E/AndroidRuntime(514): Caused by: java.lang.NullPointerException 12-04 12:14:47.467: E/AndroidRuntime(514): at np.com.njs.statusinformer.InformerHelper$Setting.grabBoolean(InformerHelper.java:115) 12-04 12:14:47.467: E/AndroidRuntime(514): at np.com.njs.statusinformer.Setup.loadPreferences(Setup.java:102) 12-04 12:14:47.467: E/AndroidRuntime(514): at np.com.njs.statusinformer.Setup.onCreate(Setup.java:31) 12-04 12:14:47.467: E/AndroidRuntime(514): at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1047) 12-04 12:14:47.467: E/AndroidRuntime(514): at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:1611) 12-04 12:14:47.467: E/AndroidRuntime(514): ... 11 more |
这是我的舱单
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 | <application android:allowBackup="true" android:debuggable="true" android:icon="@drawable/ic_launcher" android:label="@string/app_name" android:theme="@style/AppTheme"> <receiver android:name="np.com.njs.statusinformer.BootCompleteReceiver"> <intent-filter> </intent-filter> </receiver> <service android:name=".InformerService"> <intent-filter> </intent-filter> </service> <activity android:name="np.com.njs.statusinformer.Setup" android:configChanges="orientation|keyboardHidden|screenSize" android:label="@string/app_name"> <intent-filter> <category android:name="android.intent.category.LAUNCHER" /> </intent-filter> </activity> </application> |
你的
1 2 3 4 5 | public static void saveBoolean(String key, boolean value) { updater.putBoolean(key, value); updater.commit(); } |
您可以编写如下帮助方法
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 | public class MyPrefs { private static final String PREF_NAME ="My_prefs"; public static void saveBoolean(Context mContext, String key, boolean value) { SharedPreferences sharedPref = mContext.getSharedPreferences(PREF_NAME, Context.MODE_PRIVATE); SharedPreferences.Editor editor = sharedPref.edit(); editor.putBoolean(key, value); editor.commit(); } public static boolean getBoolean(Context mContext, String key) { SharedPreferences sharedPref = mContext.getSharedPreferences(PREF_NAME, Context.MODE_PRIVATE); return sharedPref.getBoolean(key, false); } } |
并用作
1 2 3 4 | // To store MyPrefs.saveBoolean(getApplicationContext(),"my_bool", true); // To read MyPrefs.getBoolean(getApplicationContext(),"my_bool"); |
发出请求后,请执行以下操作:)
1 | prefs.edit().commit(); |
通过清除所有共享的前缀(清除应用程序数据)解决了这个问题。这个问题是由数据类型的不同引起的,例如,我以布尔值的形式访问一个字符串。
您的首选项为空,因为您正在使用MyHelper类对象初始化它,而该对象不是活动。您必须提供活动实例才能初始化您的首选项。在放入值后,使用commit()完成保存操作。
检查androidmanifest.xml文件中的应用程序标记。您应该在android:name属性中正确定义类名。
1 2 | MyHelper.Setting.saveBoolean("auto_start", true); MyHelper.Setting.grabBoolean("auto_start"); |
以下方法的键应为"auto-start"。如果不是,则将引发空指针异常。
1 2 3 4 5 6 | public static boolean grabBoolean(String key) { return preferences.getBoolean(key, false); } public static void saveBoolean(String key, boolean value) { return preferences.putBoolean(key, value); } |
以下是我的应用程序中正在运行的示例
1 2 3 4 5 6 7 8 9 10 11 12 13 14 | static final String PREF_USER_NAME="USER_NAME"; public static SharedPreferences getSharedPreferences(Context ctx) { return PreferenceManager.getDefaultSharedPreferences(ctx); } public static void setUserName(Context ctx, String userid) { Editor editor = getSharedPreferences(ctx).edit(); editor.putString(PREF_USER_NAME, userid); editor.commit(); } public static String getUserName(Context ctx) { return getSharedPreferences(ctx).getString(PREF_USER_NAME,""); } |
检查应用程序清单文件,在该文件中,在应用程序标记中使用或不使用应用程序类名,建议不要将自定义应用程序类作为其他类的内部类。