Android中“@id/”和“@+id/”的区别

493

@id/@+id/有什么区别?

@+id/中,加号+表示创建一个新的资源名称并将其添加到R.java文件中,那么@id/呢?从ID文档中可以得知:当引用 Android 资源 ID 时,你不需要加上加号,但必须添加 Android 包命名空间,像这样:

android:id="@android:id/list"

然而在下面的图片中,Eclipse没有建议任何类型的@android:id/

显示@/id和@+/id建议的图片

@id/@android:id/是相同的吗?


从Android文档中:(我花了很长时间才找到这个,而且我当时是在查找一个无关的问题)https://developer.android.com/guide/topics/resources/layout-resource.html#idvalue - Juan Bonfante
12个回答

372
您提到了“Android资源”,它们已经在Android系统中定义好,并且使用“@android:id/..”来引用,而要访问您在项目中定义/创建的资源,则使用“@id/..”。
更多信息:当您使用XML属性“android:id”时,指定了一个新ID,并指示解析器(或称为构建器)在“R.java”中创建一个新条目,因此必须包含“+”符号。另一方面,如果您使用“android:layout_below = @id/myTextView”等其他情况,则是引用先前创建的ID,因此解析器将其链接到“R.java”中已经创建的ID。
再次提供更多信息:请注意,如果id为“myTextView”的元素在您正在使用它的元素之后编写,则“android:layout_below = @id/myTextView”不会识别该元素。

1
@MarcoW 非常感谢您的帮助。我之前一直在苦苦寻找这个问题的解决方案(或者说是正确的搜索关键词),您的回答对我非常有帮助。我想这个问题可能值得写成一个独立的问答形式。 - David Miler
7
我经常在android:id和android:layout_below中使用@+id/,这会有问题吗? - melanke
@melanke 我也总是这样做。从来没有出过问题。但我想知道它是否有任何影响,无论多么不起眼。 - RestInPeace
@RestInPeace也许应用程序通过这样做会使用更多的内存。但是我已经按照这种模式发布了很多应用程序,所以我不担心它。 - melanke
5
将“+”符号放入layout_belowandroid:id也是非常好的,因为正如Tanmay Mandal在他的回答中提到的那样,“+”意味着如果该符号不存在,就创建该符号。因此,这也不会产生任何负面运行效果(尽管可能会略微增加编译时间^^)。 - Levite
显示剩余2条评论

91

加号(+)是将id添加到资源id列表的快捷方式。否则,您需要在xml文件中像这样定义它们:

<?xml version="1.0" encoding="utf-8"?>
<resources>
    <item name="my_logo" type="id"/>
</resources>

1
@schwiz:那我们如何在布局中使用它? - Vikas Patidar
7
假设您拥有我在答案中定义的资源文件,那么在您的布局中,您可以使用 <View android:id="@id/my_logo"/>。如果您没有我上面定义的资源文件,则需要这样写 <View android:id="@+id/my_logo"/>。注意:您只需要在第一次使用时使用 +id,因此如果在另一个布局文件中使用了 <View android:id="+id/my_logo"/>,则下次在布局中再次使用相同的id时就不需要包含 '+' 字符。 - Nathan Schwermann
@schwiz:好的,这很有用。但是我们必须把那个文件放在哪里 res/drawable/ 还是 res/layout/ 或者 res/values/?那个文件的名称是什么?如果您有任何有用的链接,请在此处发布。 - Vikas Patidar
1
这里是关于资源命名规范等方面的一切需要了解的内容。你需要将文件放在res/values/目录下,惯例是将其命名为ids,但你可以随意更改名称。详见http://developer.android.com/guide/topics/resources/providing-resources.html。 - Nathan Schwermann

49

简而言之

android:id="@+id/my_button"

+id表示告诉Android在资源中添加或创建一个新的ID。

android:layout_below="@id/my_button"

它只是帮助引用已生成的ID。


11

9
在定义资源ID时,只有在第一次定义资源ID时需要在资源类型前加上加号(+)。编译应用程序时,SDK工具将使用该ID名称在项目的R.java文件中创建一个新的资源ID,该资源ID指向EditText元素。通过这种方式仅声明一次资源ID,其他对该ID的引用不需要加上加号。只有在指定新的资源ID时才需要使用加号,对于像字符串或布局这样的具体资源则不需要。有关资源对象的更多信息,请参见侧边栏。
来源: https://developer.android.com/training/basics/firstapp/building-ui.html

6
@+id@id 的区别是:
  • @+id 用于在 R.java 文件中为视图创建一个 ID。
  • @id 用于引用在R.java文件中为视图创建的ID。

我们在使用 android:id="" 时需要使用 @+id,但如果在创建之前引用了未创建的ID(前向引用),怎么办?

在这种情况下,我们需要使用@+id 来创建ID,并在定义视图时引用它。

请参考以下代码:

<RelativeLayout>

     <TextView
        android:id="@+id/dates"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignParentLeft="true"
        android:layout_toLeftOf="@+id/spinner" />

   <Spinner
     android:id="@id/spinner"
     android:layout_width="96dp"
     android:layout_height="wrap_content"
     android:layout_below="@id/dates"
     android:layout_alignParentRight="true" />

</RelativeLayout>

在上述代码中,Spinner 的 id @+id/spinner 在其他视图中创建,在定义 Spinner 时我们引用了上面创建的 id。
因此,如果我们在创建视图之前使用该视图,则必须创建该 id。

6

来自开发者指南


android:id="@+id/my_button"

字符串开头的“@”符号表示XML解析器应该解析并展开ID字符串的其余部分,并将其识别为ID资源。“+”符号表示这是一个新的资源名称,必须添加到我们的资源中(在“R.java”文件中)。Android框架提供了许多其他ID资源。当引用Android资源ID时,您不需要加上“+”符号,但必须添加“android”包命名空间,如下所示:android:id="@android:id/empty"

4

@id/@android:id/不是同一个东西。

@id/用于引用应用程序中的ID,@android:id/用于引用Android平台中的项目。

Eclipse错了。


你是在说 **@id/ 引用应用程序中的ID**,但是当我们使用它来引用应用程序资源时,Eclipse会给出“找不到与给定名称匹配的资源(位于'value'为'@id/my_resource_id'的'id'处)”的错误。那么 @id/@+id/ 之间有什么区别?你怎么能说Eclipse是错的呢? - Vikas Patidar
1
Eclipse在不显示@android:id建议时是错误的。如果您在没有使用@+id/myId声明它的情况下使用@id/myId,则您也是错误的。所有@id/xxx都必须在应用程序中的某个地方使用@+id/xxx进行声明。 - Olegas
感谢您的澄清。我认为这里Eclipse没有错,而是根据我们布局元素的上下文显示建议。它只在RelativeLayout的情况下显示“@id/”。 - Vikas Patidar

4
Android使用一些名为资源的文件,存储XML文件的值。当您在XML对象中使用@id/时,它试图引用已在值文件中注册的ID。另一方面,当您使用@+id/时,它会在值文件中注册一个新的ID,这由'+'符号表示。希望这可以帮到您 :)。

4

Eclipse存在一个bug,有时如果你刚刚创建了一个新的@+id/..,即使在清除项目并重新构建之后,它也不会立即添加到R.java文件中。解决方法是重启Eclipse。

我认为应该尽快解决这个问题,因为它可能(并且根据经验,确实会)让一些开发人员以为他们的语法有问题,即使没有任何需要调试的内容。


3
我转用 Android Studio 的原因之一是它让我很满意,再也没有想过回头了 :)(我知道你回答时还没有它) - Konrad Morawski

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接