使用Java构建多语言应用程序。从R.string
资源XML文件插入字符串值时出错:
public static final String TTT = (String) getText(R.string.TTT);
这是错误消息:
错误:无法从类型中对非静态方法getText(int)进行静态引用 上下文
这是如何引起的?如何解决?
答案 0 :(得分:136)
由于getText()
是非静态的,因此无法通过静态方法调用它。
要了解原因,您必须了解两者之间的区别。
实例(非静态)方法适用于特定类型(类)的对象。这些是用这样的新东西创建的:
SomeClass myObject = new SomeClass();
要调用实例方法,请在实例(myObject
)上调用它:
myObject.getText(...)
但是静态方法/字段可以直接在类型上被称为 ,比如说:
之前的陈述不正确。 One can also refer to static fields with an object reference like myObject.staticMethod()
但不鼓励这样做,因为它并不清楚它们是类变量。
... = SomeClass.final
两者无法协同工作,因为它们在不同的数据空间(实例数据和类数据)上运行
让我试着解释一下。考虑这个类(伪代码):
class Test {
string somedata = "99";
string getText() { return somedata; }
static string TTT = "0";
}
现在我有以下用例:
Test item1 = new Test();
item1.somedata = "200";
Test item2 = new Test();
Test.TTT = "1";
有什么价值?
好
in item1 TTT = 1 and somedata = 200
in item2 TTT = 1 and somedata = 99
换句话说,TTT
是该类型的所有实例共享的数据。所以说
class Test {
string somedata = "99";
string getText() { return somedata; }
static string TTT = getText(); // error there is is no somedata at this point
}
所以问题是为什么 TTT 是静态的还是为什么getText()不是静态的?
删除static
并且它应该通过此错误 - 但是如果不了解你的类型是什么,它只是一个粘贴膏药,直到下一个错误。 getText()
要求它是非静态的要求是什么?
答案 1 :(得分:11)
已经有一些很好的答案,解释了为什么非静态Context
方法getText()
的混合不能与static final String
一起使用。
一个很好的问题是:你为什么要这样做?您正在尝试从String
资源加载strings
,并将其值填入public static
字段。我认为这是为了让你的其他一些类可以访问它?如果是这样,就没有必要这样做了。而是将Context
传递到其他类中,然后从其中调用context.getText(R.string.TTT)
。
public class NonActivity {
public static void doStuff(Context context) {
String TTT = context.getText(R.string.TTT);
...
}
}
并从您的Activity
NonActivity.doStuff(this);
这样,您无需使用String
字段即可访问public static
资源。
答案 2 :(得分:8)
其他在搜索中找到此内容的人:
当我不小心使用类名而不是对象名调用函数时,我经常得到这个。这通常是因为我给他们太相似的名字:P
即:
MyClass myclass = new MyClass();
// then later
MyClass.someFunction();
这显然是一种静态方法。 (适合某些人) 但我真正想做的事情(在大多数情况下是)
myclass.someFunction();
这是一个如此愚蠢的错误,但是每隔几个月,我浪费了大约30分钟来处理“MyClass”定义中的变量,以便弄清楚我真正做错了什么,这只是一个错字。
有趣的是:堆栈溢出突出了语法,使错误在这里显而易见。
答案 3 :(得分:2)
您可以使变量非静态
public final String TTT = (String) getText(R.string.TTT);
或将“getText”方法设为静态(如果可能的话)
答案 4 :(得分:2)
getText是您的Activity的成员,因此必须在" this"存在。在创建Activity之前加载类时,会初始化静态变量。
由于您希望从资源字符串初始化变量,因此它不能是静态的。如果您希望它是静态的,可以使用String值初始化它。
答案 5 :(得分:2)
您无法从非静态方法引用静态变量。 要理解这一点,您需要了解静态和非静态之间的区别。
静态变量是类变量,它们属于只有一个实例的类,仅在第一个实例上创建。 每次创建类的对象时都会初始化非静态变量。
现在回答您的问题,当您使用new()运算符时,我们将为每个对象创建每个非静态字段的副本,但静态字段不是这种情况。这就是为什么如果从非静态方法引用静态变量,它会给出编译时错误。
答案 6 :(得分:0)
这个问题并不新鲜,现有的答案给出了一些很好的理论背景。我只想添加一个更实用的答案。
getText是Context抽象类的一种方法,为了调用它,需要一个它的子类(Activity,Service,Application或其他)的实例。问题是,在创建Context的任何实例之前初始化公共静态最终变量。
有几种方法可以解决这个问题:
答案 7 :(得分:-1)
您不能使用非静态方法初始化静态变量。