【问题标题】:Which Architecture patterns are used on Android? [closed]Android 上使用了哪些架构模式? [关闭]
【发布时间】:2011-06-22 10:04:34
【问题描述】:

我正在对移动平台进行一项小型研究,我想知道 Android 中使用了哪些设计模式?

例如在 iOS 中 Model-view-controller 与委托和其他模式一起使用非常广泛。

Android 使用哪些模式以及具体在哪里使用?

编辑

我问的不是在内核、dalvik 等中使用的设计模式,而是应用程序开发人员在开发应用程序时会遇到的模式。

【问题讨论】:

  • 鉴于 Android 平台包含一个 Linux 内核,它的软件套件太大而无法回答这个问题,除了“到目前为止命名的所有模式,如果你仔细观察可能还有一些新模式”够了'
  • @Pete,好吧,也许你是对的,但同时我没有像内核那样深入,我对应用程序的表面感兴趣,例如在 iOS 中,UIViewController 使用 MVC 实现(UIViewController 是一个控制器,它的根 UIView 是视图),UIApplication 使用委托,将 Application Delegate 作为委托等等......
  • 我认为你应该真正从下往上学习Android,而不是试图将你的知识从iOS“移植”到Android。那里有很多很棒的书。 Apress 做了一堆。如果您了解 android 中的应用程序和服务生命周期,您应该能够了解如何正确设计应用程序。
  • 这可能会有所帮助:stackoverflow.com/a/49694378

标签: android design-patterns


【解决方案1】:

我尝试使用model–view–controller (MVC) 和model–view–presenter 架构模式进行android 开发。我的发现是模型-视图-控制器工作正常,但有几个“问题”。这一切都取决于您如何看待 Android Activity 类。是控制器,还是视图?

实际的 Activity 类没有扩展 Android 的 View 类,但是它确实处理向用户显示窗口并处理该窗口的事件(onCreate、onPause 等)。

这意味着,当您使用 MVC 模式时,您的控制器实际上是一个伪视图控制器。由于它正在处理向用户显示一个窗口,以及您使用 setContentView 添加到其中的其他视图组件,并且还处理至少各种活动生命周期事件的事件。

在 MVC 中,控制器应该是主入口点。如果将其应用于 Android 开发时,这有点值得商榷,因为 Activity 是大多数应用程序的自然入口点。

正因为如此,我个人觉得model-view-presenter模式非常适合Android开发。由于视图在此模式中的作用是:

  • 作为入口点
  • 渲染组件
  • 将用户事件路由到演示者

这允许您像这样实现您的模型:

View - 这包含您的 UI 组件,并为它们处理事件。

Presenter - 这将处理模型和视图之间的通信,将其视为通往模型的网关。意思是,如果你有一个复杂的领域模型表示,天知道是什么,而你的视图只需要这个模型的一个很小的子集,那么演示者的工作就是查询模型然后更新视图。例如,如果您的模型包含一段文本、一个标题和一个字数。但是在给定的视图中,您只需要在视图中显示标题即可。然后 Presenter 将从模型中读取所需的数据,并相应地更新视图。

模型 - 这基本上应该是您的完整域模型。希望它也有助于使您的域模型更加“紧凑”,因为您不需要特殊的方法来处理上述案例。

通过将模型与视图完全解耦(通过使用演示器),测试模型也变得更加直观。您可以为您的领域模型进行单元测试,并为您的演示者进行单元测试。

试试看。我个人觉得它非常适合 Android 开发。

【讨论】:

  • 很好的答案!不过我有疑问: 1. Activity = View,我做对了吗? 2. 你会将presenter实现为自己的公共类,还是Activity的内部类?还是一个片段(也是内部类)? 3. 你的意思是在Activity(视图)中应该使用传输类而不是实际的模型类?
  • 1.是的,我将它们用作 MVP 模式中的视图。 2. 就个人而言,我将它们分成单独的公共课程,但我想这是一个品味问题:) 3. 我解释得很糟糕,“转发所需的课程”这句话具有误导性。我的意思是,演示者位于视图和模型之间,它读取模型然后更新视图。我会更新我的答案以更清楚:)
  • 感谢您抽出宝贵时间,我现在明白了 :)
  • 我真的很喜欢 Android 开发,因为它是高度解耦的。我如何使用 MVC:将活动纯粹用于用户 IO,并使用本地服务进行所有处理。当服务想要显示某些东西时 - 将其广播到您的活动中!当其他开发人员在活动中投入过多的处理时,我真的很讨厌它。
  • @SomeoneSomewhere 为什么没有一个在单独的线程/AsyncTasks 中处理这些东西的类,为什么是服务?
【解决方案2】:

2018 年 11 月更新

在 Android 中的 MVC 和 MVP 工作和撰写博客数年之后(请参阅下面的答案正文),我决定以更全面、更易于理解的形式记录我的知识和理解。

因此,我发布了有关 Android 应用程序架构的完整视频课程。所以,如果你有兴趣掌握 Android 开发中最先进的架构模式,check out this comprehensive course here。

此答案已更新,以便在 2016 年 11 月保持相关性


您似乎在寻找 architectural patterns 而不是 design patterns。

设计模式旨在描述程序员为处理一组特定的重复性软件任务可能实施的一般“技巧”。例如:在OOP中,当需要一个对象通知一组其他对象某些事件时,可以使用observer design pattern。

由于 Android 应用程序(以及大多数 AOSP)是用 Java 编写的,Java 是面向对象的,我认为您将很难找到一种未在 Android 上使用的单一 OOP 设计模式。

另一方面,

架构模式并不针对特定的软件任务——它们旨在根据软件组件的用例为软件组织提供模板问题。

听起来有点复杂,但我希望举个例子来说明一下:如果某个应用程序将用于从远程服务器获取数据并以结构化的方式呈现给用户,那么MVC 可能是一个不错的选择审议。请注意,我没有提到应用程序的软件任务和程序流程——我只是从用户的角度描述了它,并且出现了一种架构模式的候选者。

由于您在问题中提到了 MVC,我猜您正在寻找架构模式。


从历史上看,Google 没有关于应用程序架构的官方指南,这(除其他原因外)导致 Android 应用程序的源代码完全混乱。事实上,即使在今天,我看到的大多数应用程序仍然没有遵循 OOP 最佳实践,也没有显示出清晰的代码逻辑组织。

但今天情况不同了——谷歌最近发布了Data Binding library,它与Android Studio完全集成,甚至推出了一套architecture blueprints for Android applications。

两年前,很难找到有关 Android 上的 MVC 或 MVP 的信息。如今,MVC、MVP 和 MVVM 已经成为 Android 社​​区的“流行语”,我们周围有无数专家不断试图说服我们 MVx 比 MVy 更好。在我看来,讨论 MVx 是否比 MVy 更好是完全没有意义的,因为这些术语本身非常模棱两可——只要看看this question 的答案,你就会意识到不同的人可以将这些缩写与完全不同的结构联系起来。

由于已经正式开始寻找适用于 Android 的最佳架构模式,我想我们即将看到更多的想法浮出水面。在这一点上,真的无法预测未来哪种模式(或哪些模式)会成为行业标准——我们需要拭目以待(我猜是一两年的事情)。

但是,我可以高度自信地做出一个预测:数据绑定库的使用不会成为行业标准。我有信心这样说,因为 Data Binding 库(在其当前实现中)提供了短期的生产力提升和某种架构指南,但从长远来看它会使代码不可维护。一旦这个库的长期影响浮出水面 - 它就会被放弃。


现在,虽然我们今天确实有一些官方指南和工具,但我个人认为这些指南和工具并不是最好的选择(而且它们绝对不是唯一的)。在我的应用程序中,我使用自己的 MVC 架构实现。它简单、干净、可读和可测试,并且不需要任何额外的库。

此 MVC 不仅在外观上与其他 MVC 不同 - 它基于 Activities in Android are not UI Elements 的理论,这对代码组织具有巨大的影响。

因此,如果您正在为遵循 SOLID 原则的 Android 应用程序寻找良好的架构模式,您可以在我关于 MVC and MVP architectural patterns in Android 的帖子中找到其中的描述。

【讨论】:

  • 提供这样的资源做得很好!谢谢!
  • 非常有用的链接!
  • 我喜欢你的视频课程!谢谢
【解决方案3】:

当我看到这篇文章时,它确实帮助我通过示例来理解模式,因此我制作了下表以清楚地看到设计模式及其在 Android 框架中的示例

希望对您有所帮助。

【讨论】:

  • 请edit您的帖子并将实际内容显示为文本而不是屏幕截图。其他人无法从您的图像中复制和粘贴,也无法帮助您修正拼写错误。 See here 了解详情。谢谢。
  • 谢谢你的回答我对架构模式和设计模式感到很困惑,我还有一个问题,什么是oo-design and development!? @彼得沃尔特
  • 我赞成这个答案,因为尽管@Burjua 的问题通过引用架构来提到设计模式,但它们并不相同。我认为这个答案非常有用,并且与原始问题互补
  • 事件总线使用发布者和订阅者设计模式
【解决方案4】:

Android 框架中使用了多种模式,例如:

  • 广播接收器使用观察者模式
  • 远程服务调用使用代理模式
  • 视图和视图组使用复合模式
  • 媒体框架使用 Facade 模式

【讨论】:

  • 能否请您分享链接(参考)
  • 请分享参考资料,以便我找到更多相关信息。谢谢
【解决方案5】:

这是Common Design Patterns for Android上的一篇很棒的文章:

创作模式:

  • 生成器(例如 AlertDialog.Builder)
  • 依赖注入(例如Dagger 2)
  • 单例

结构模式:

  • 适配器(例如 RecyclerView.Adapter)
  • 立面(例如改造)

行为模式:

  • 命令(例如 EventBus)
  • 观察者(例如 RxAndroid)
  • 模型视图控制器
  • Model View ViewModel(类似于上面的 MVC 模式)

【讨论】:

  • 文章中的关键点会很好。
  • 虽然这在理论上可以回答问题,it would be preferable 在此处包含答案的基本部分,并提供链接以供参考。
  • 事件总线使用发布者和订阅者设计模式
【解决方案6】:

以下 Android 类使用设计模式

1) View Holder 使用单例设计模式

2) Intent 使用工厂设计模式

3) 适配器使用适配器设计模式

4) 广播接收器使用观察者设计模式

5) 视图使用复合设计模式

6) 媒体框架使用外观设计模式

【讨论】:

    【解决方案7】:

    在Notifications 的情况下,NotificationCompat.Builder 使用Builder Pattern

    喜欢,

    mBuilder = new NotificationCompat.Builder(this)
                        .setSmallIcon(R.drawable.ic_stat_notification)
                        .setContentTitle(getString(R.string.notification))
                        .setContentText(getString(R.string.ping))
                        .setDefaults(Notification.DEFAULT_ALL);
    

    【讨论】:

    • 这实际上是Builder模式。
    • @Piovezan 我错了。谢谢你纠正我。我认为这是装饰器模式的简单版本。
    【解决方案8】:

    Android 也使用 ViewHolder 设计模式。

    它用于提高 ListView 在滚动时的性能。

    ViewHolder 设计模式使您无需查找即可访问每个列表项视图,从而节省宝贵的处理器周期。具体来说,它避免了在 ListView 滚动过程中频繁调用 findViewById() ,这将使其平滑。

    【讨论】:

      【解决方案9】:

      所有这些模式,MVC、MVVM、MVP 和Presentation Model,都可以应用于 Android 应用程序,但没有第三方框架,很难获得组织良好的结构和干净的代码。

      MVVM 源自 PresentationModel。当我们将 MVC、MVVM 和 Presentation Model 应用到 Android 应用时,我们真正想要的是有一个清晰的结构化项目,更重要的是更容易进行单元测试。

      目前,在没有第三方框架的情况下,通常会有很多代码(如 addXXListener()、findViewById() 等),这些代码不会增加任何业务价值。更重要的是,您必须运行 Android 单元测试而不是普通的 JUnit 测试,这需要很长时间才能运行并且使单元测试有些不切实际。

      出于这些原因,几年前我们启动了一个开源项目,RoboBinding - Android 平台的数据绑定表示模型框架。 RoboBinding 可帮助您编写更易于阅读、测试和维护的 UI 代码。 RoboBinding 消除了addXXListener 等不必要的代码 的需要,并将UI 逻辑转移到表示模型,这是一个POJO,可以通过普通的JUnit 测试 进行测试。 RoboBinding 本身带有 300 多个 JUnit 测试以确保其质量。

      【讨论】:

        【解决方案10】:

        我想添加一个已在 Android 框架中应用的设计模式。这是 Asynctask 实现中使用的半同步半异步模式。请参阅我在

        上的讨论

        https://docs.google.com/document/d/1_zihWXAwgTAdJc013-bOLUHPMrjeUBZnDuPkzMxEEj0/edit?usp=sharing

        【讨论】:

          【解决方案11】:

          在 Android 中,“工作队列处理器”模式通常用于从应用程序的主线程卸载任务。

          示例:IntentService 类的设计。

          IntentService 接收 Intent,启动工作线程,并根据需要停止服务。所有请求都在单个工作线程上处理。

          【讨论】:

            【解决方案12】:

            Binder 对死亡收件人通知使用“观察者模式”。

            【讨论】:

              猜你喜欢
              • 1970-01-01
              • 2014-02-26
              • 1970-01-01
              • 1970-01-01
              • 2010-09-06
              • 2021-07-28
              • 2012-09-08
              • 1970-01-01
              相关资源
              最近更新 更多