确定使用私有的构造函数中的活动,所以我可以用final修饰符的变量?可以用、变量、函数、所以我

2023-09-12 06:03:20 作者:劳资拽你管不着

整个原来的问题是基于一个错误。你永远无法分配的最后的静态字段在构造函数中常量的值。如果你能,你将有静态字段的值的更改的每一个创建类的新实例时。不是很决赛!

我能,而不是做什么,我一直在做(和可能产生内存泄漏,我有很多东西需要学习),这是使用静态(而不是最后)字段设置为指向我的活动的最新实例(请参见下面的code样品)。正如下面的评论会谈的内存泄漏所指出的,我几乎可以肯定已经通过保持引用我的大活动对象围绕创建内存泄漏。

所以,答案我原来的问题真的可以归结为:这不是一个很好的事情,因为交给其他对象的引用我目前的活动对象使他们能够保持系统从以往的垃圾收集我的旧的活动对象

总之,这里是code。在我原来的问题提到,答案和评论还是在这里,所以这剩下的就是保存提及这些。

 公共类MyActivity延伸活动{
  公共最后静态MyActivity UI;
  公共静态MyActivity mostRecentUI;

  私人MyActivity(){//这是构造函数
      //在我原来的职位我有:
      // UI =这一点;
      //但是这是违法的code。 `最后的静态东西;`不能分配
      //在构造函数中的价值,因为它可以被赋予不同的值
      //每一次的类实例化!

      //而不是最好的,我能做的就是
      mostRecentUIobject =这一点;
      //这个名字更好地描述了这个静态变量包含
  }

  @覆盖
  保护无效的onCreate(包savedInstanceState){
      super.onCreate(savedInstanceState);
      的setContentView(R.layout.main);
  }
}
 

补充4/15:@dmon竟把评论,构造函数将不会运行。它会和任何人有任何疑问,可以运行这个测试活动:

 公共类TestActivityConstructor延伸活动{
    静态长refTime = System.currentTimeMillis的();
    静态字符串staticExecution =静从来没有执行\ n;
    静态字符串constructorExecution =构造从未执行\ n;
    静态字符串onCreateExecution =的onCreate从未执行\ n;

    静态{
        staticExecution = +在静态执行​​(System.currentTimeMillis的() -  refTime)+MS \ N的;
    }

    公共TestActivityConstructor(){
        constructorExecution =构造函数在执行+(System.currentTimeMillis的() -  refTime)+MS \ N的;
    }

    @覆盖
    公共无效的onCreate(包savedInstanceState){
        onCreateExecution =的onCreate在执行+(System.currentTimeMillis的() -  refTime)+MS \ N的;
        super.onCreate(savedInstanceState);
        的setContentView(R.layout.main);
        ((TextView中)findViewById(R.id.TV))的setText(staticExecution + constructorExecution + onCreateExecution)。
    }
}
 

显然,你需要一个简单的layout.xml一个叫做电视的TextView。没有权限需要。你甚至可以有乐趣旋转你的android看到应用程序显示出重新创建的,无论是构造函数和的onCreate重新运行每屏幕旋转时间,但是,当活动被重新静态分配是不重做。

解决方案 十分钟深刻理解Java高级特性 反射

要基本上回答您的问题标题的主要部分...

  

确定使用私有的构造函数的活动......?

没有。

我假设你来从previous Java的待机点,但有一件事要了解关于Android到Android的是,活动类是中应留给工作,因为他们正在设计一些特殊情况下的类。

不关心自己与构造函数的概念,当它涉及到了活动类只要按照设计方法和应用基础这相当充分的工作。

如果您有没有Android的框架内开展工作的具体要求,然后张贴与例如code和别人的问题将解释如何解决它。

编辑:鉴于你更新你的问题......

 公共最后静态MyActivity UI;
 

  

有了这个地方,我可以返回到用户界面对象MyActivity.uI,而无需通过调用链传递引用。

说真的......不这样做。有哪些可以用来方便地处理以最小的code任何情况下,没有'破'的模式,你正在试图做的事情的方式完全够用,实用,安全的机制。

要重复一下我上面说的我原来的答复 - 在Android 活动类是一个特例。对活动及其方法实例/字段并不是直接由任何其他外部类的访问。

您会做自己一个忙,节省了很多麻烦,如果你简单地接受了Android框架的基本原则。编码Android应用程序可能涉及的Java,但不是所有的通用的Java应用的概念,特别是一些核心部件,如活动

The entire original question was based on a mistake. You can NEVER assign the value of a final static FIELD constant in the constructor. If you could, you would have the value of the static FIELD changing every time a new instance of the class was created. Not very final!

I can instead do what I have been doing (and possibly creating memory leaks, I have a lot to learn), which is to use a static (but not final) field to point to the most recent instance of my Activity (see the code sample below). As the comment below that talks of memory leaks points out, I almost certainly have been creating memory leaks by keeping references to my older Activity objects around.

So the answers to my original question really comes down to: this is not a good thing to do because handing other objects references to my current Activity object allows them to keep the system from ever garbage collecting my old Activity objects!

Anyway, here is the code referred to in my original question, the answers and comments are still here so the rest of this is kept for reference to those.

public class MyActivity extends Activity {
  public final static MyActivity uI;
  public static MyActivity mostRecentUI;

  private MyActivity() { // this is the constructor
      // In my original post I had:
      // uI = this;  
      // but this is illegal code.  `final static anything;` cannot be assigned a 
      // value in the constructor, because it could be assigned a different value
      // each time the class is instantiated!  

      // Instead the best I can do is
      mostRecentUIobject = this;
      // and this name better describes what this static variable contains
  }

  @Override
  protected void onCreate(Bundle savedInstanceState) {
      super.onCreate(savedInstanceState);
      setContentView(R.layout.main);
  }
}

Added 4/15: @dmon goes as far as to comment that the constructor won't be run. It will, and anybody with any doubt can run this test activity:

public class TestActivityConstructor extends Activity {
    static long refTime = System.currentTimeMillis();
    static String staticExecution = "Static never executed\n";
    static String constructorExecution = "Constructor never executed\n";
    static String onCreateExecution = "onCreate never executed\n";

    static {
        staticExecution = "Static Execution at " + (System.currentTimeMillis() - refTime) + " ms\n";
    }

    public TestActivityConstructor() {
        constructorExecution = "Constructor Execution at " + (System.currentTimeMillis() - refTime) + "ms \n";
    }

    @Override
    public void onCreate(Bundle savedInstanceState) {
        onCreateExecution = "onCreate Execution at " + (System.currentTimeMillis() - refTime) + "ms \n";
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);
        ((TextView) findViewById(R.id.TV)).setText(staticExecution + constructorExecution + onCreateExecution);
    }
}

Obviously, you need a trivial layout.xml with a textview called TV. No permissions needed. You can even have fun rotating your android to see the app recreated showing that both the constructor and the onCreate are re-run every time the screen is rotated, but that the static assignments are NOT redone when the Activity is recreated.

解决方案

To basically answer the main part of your question title...

OK to use private constructor in Activity...?

No.

I'm assuming you're coming to Android from a previous Java stand-point but one thing to understand about Android is that the Activity class is one of a few special case classes which should be left to work as they're designed to.

Don't concern yourself with the concept of constructors when it comes to the Activity class just follow the design methodologies and application fundamentals which work quite adequately.

If you have a specific requirement which doesn't work within the Android framework then post a question with example code and somebody will explain how to fix it.

EDIT: In light of your update to your question...

public final static MyActivity uI;

With this in place, I can refer back to the "user interface" object as MyActivity.uI without having to pass references through chains of calls.

Seriously...don't do that. There are perfectly adequate, functional and safe mechanisms which can be used to easily handle any situation with minimal code without 'breaking' the model in the way you're attempting to do things.

To repeat what I said above in my original answer - the Android Activity class is a special case. Instances of Activity and their methods/fields are not meant to be accessed directly by any other external class.

You'll be doing yourself a favour and save a lot of headaches if you simply accept the fundamentals of the Android framework. Coding Android apps may well involve Java but not all 'generic' Java concepts apply, in particular to some of the core components such as Activity.