博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Integrate Your Code with the Frameworks---整合你的代码和框架
阅读量:5174 次
发布时间:2019-06-13

本文共 20422 字,大约阅读时间需要 68 分钟。

Integrate Your Code with the Frameworks

When you develop an app for OS X or iOS, you won’t be on your own. You’ll be drawing on the work done by Apple and others, on the classes they’ve developed and collected in Objective-C frameworks. A framework is a class library that can be shared by multiple processes at runtime; it includes the resources that support software development with that library. The Cocoa and Cocoa Touch frameworks give you a set of interdependent classes that work together to structure a part—often a substantial part—of your app.

当你开发一个OS X 或 iOS 应用程序时,你不会就靠你自己。 你将借助Apple 和 其它人所制作的各种类,这些类被收集在Objective-C框架里。 一个框架是一个类库,该类库能在runtime同时被多个进程所共享;它包含了支持用该库进行软件开发的各种资源。 Cocoa 和 Cocoa Touch框架给你提供了一组相互依存的类,它们一起工作构成你应用程序的一部分--往往是一个主要部分。

With a library of C functions, you can more or less pick and choose which functions to use and when to call them, depending on the program you’re trying to write. A framework, on the other hand, imposes a design on your program, or at least on a certain problem space your program is trying to address. When using an object-oriented framework, you can call methods of the framework’s classes to do much of the work of the program, just as in a procedural program. But you’ll also need to customize the generic framework behavior and adapt it to your needs by implementing methods that the framework will invoke at the appropriate time. These methods are hooks that introduce your code into the structure imposed by the framework, augmenting it with the behavior that characterizes your program.

 使用一个C函数库,你可以或多或少挑选几个函数使用,当你调用它们时,取决于你想编写的程序。另一方面,框架决定了你程序的一个设计,或者至少决定了一个你程序想要处理的目标问题空间。当你使用一个面向对象的框架时,你可以调用该框架里各种类的各种方法来完成程序里的很多动作,就像一个程序的程序。但是你也将需要定制该框架的通过框架行为,然后通过在合适的时候实现框架中的各种方法以适应你的需求。这些方法把你的代码引入(introduce)被框架所规定(imposed)的结构中,和框架行为一起描述你的程序。

The following sections explore this relationship between framework code and application code.

以下章节探索框架代码和应用程序代码之间的关系。

Apps Are Driven by Events

应用程序是由事件驱动的

You can gain some insight into the relationship between your code and framework code by considering what takes place when an application launches. Basically, the app sets up a core group of objects and turns control over to those objects. More and more objects will be created as the program runs, but at the outset all that’s required is enough structure—that is, enough of the core object network—to handle the initial tasks. There are two primary tasks:

通过考虑当一个应用程序启动时发生了什么,可以洞察一些你的代码跟框架代码之间的关系。基本上,应用程序启动对象的核心组(core group), 然后把控制权移交给这些对象。 当程序运行时,越来越多的对象将被创建, 但是在一开始所有的需求是足够的结构---就是足够的核心对象网络---用来处理初始化任务。 它有两项主要任务:

  • Draw the app’s initial user interface.

    绘制应用程序初始用户界面

  • Handle the events received when the user interacts with that user interface.

    当用户跟那个用户界面交互时,处理接收到的各种事件

After the initial user interface is on the screen, the app is driven by external events, the most important of which are those originated by users (for example, by clicking a button). The operating system reports such events, along with information about them, to the app. The app, consisting of both your code and that of the frameworks, handles the events and updates the user interface accordingly.

当初始用户界面显示在屏幕上以后, 应用程序由外部事件驱动, 这些外部事件都源于用户(比如,点击按钮)。操作系统向应用程序报告这些事件,以及跟它们有关的各种信息。 由你的代码以及框架代码组成的应用程序处理这些事件,从而更新用户界面。

An app gets an event and responds to it, often by drawing a part of the user interface. It then waits for the next event. It keeps getting events, one after another, as long as the user or some other source (such as a timer) initiates them. From the time an app is launched to the time it terminates, almost everything it does is driven by user actions in the form of events.

应用程序获取一个事件并对它做出回应,通常是通过绘制用户界面的一部分。 然后它又等待下个事件。 它一个接着一个的获取事件,只要用户或者一些别的资源(比如一个定时器)触发它们。应用程序从启动到停止,它做的所有事情几乎都是由用户动作以事件的形式驱动的。

The mechanism for getting and responding to events is the main event loop. In the group of core objects of an app, one object, the global app object, is responsible for managing the main event loop; it gets an event, dispatches the event to the object or objects that can best handle it, and then gets the next event. This figure illustrates the main event loop for Cocoa apps in OS X.

获取并响应各种事件的机制是主要事件循环。 在应用程序的核心对象组里,有一个全局应用对象负责该主要事件循环;它获取一个事件 ,并把它分发给一个或一个能对它做出最好处理的对象,然后获取下一个事件。 下图显示了OS X 中 Cocoa 应用程序的主要事件循环。

The main event loop (Mac OS X)

Using an Object-Oriented Framework

使用一个面向对象框架

The Cocoa and Cocoa Touch frameworks are more than a grab bag of individual classes that offer their services. They contain object-oriented frameworks, which are collections of classes that structure a problem space and present an integrated solution to it. Instead of providing discrete services that you can use as needed (as with function libraries), a framework maps out and implements an entire application structure that your own code must adapt to. Because this application structure is generic, you can specialize it to meet the requirements of your particular app. Rather than design an app that you plug library functions into, you plug the code for your app code into the design provided by the framework.

Cocoa 和 Cocoa Touch 框架拥有各种各样的独特类来提供它们的服务。 它们包含各种面向对象的框架,框架收集了解决一个问题空间的各种类,并提供了一个完整的解决方法。框架设计并实现了一整个应用程序结构,而不是提供当你需要的能够使用的各种松散服务(比如 函数库),你编写的代码必须能够适应这个结构。因为这个应用程序结构是通用的,所以你可以专注于让它符合你的特殊应用程序的需求。你往框架提供的设计里插入你的应用程序代码,而不是设计一个你向它插入库函数的应用程序。

To use a framework, you must accept the application structure it defines and then employ and customize as many of its classes as necessary to mold your particular app to that structure. The classes of a framework are mutually dependent and come as a group, not individually. At first glance, the need to adapt your code to a framework’s structure for apps might seem restrictive. But the reality is quite the opposite. A framework offers you many ways in which you can alter and extend its generic behavior. It simply requires you to accept that all apps behave in the same fundamental ways because they are all based on the same structure. In a broad metaphorical sense, an Objective-C framework is like the framework of a house, and your app code is like the doors, windows, siding, and other elements that make the house unique.

想要使用一个框架,你必须结构它定义的应用程序结构,然后雇佣并定制(customize)尽可能多的框架类来往那个结构里铸造(mold)你的特殊应用程序。 一个框架里的所有类都是相互依赖并作为一个群体出现,它们不是相互独立的。乍一看,应用程序中让你的代码适应一个框架的结构可能是受限制的。 但是现实中它是完全相反的。 框架提供了很多方法让你转换和扩展它的通用行为。 它只简单要求你以相同的基础方式接受所有的应用程序行为,因为它们都基于相同的结构。用比喻来说,一个Objective-C框架就像一个房子的框架, 而你的代码就像门, 窗口,滑槽,以及让这房子变得独特的其他各种元素。

image: ../Art/house_framework.png

From the perspective of using a framework and integrating your code with it, there are two general kinds of classes.

透过使用一个框架并集成你的代码,有两种基本类型的类(classes)。

  • Off the shelf. Some classes define off-the-shelf objects—that is, objects that are ready to be used. You simply create instances of the class and use the instances as needed.

    Off the shelf. 一些类定义off-the-shelf 对象---就是,即将被使用的对象。 你简单的创建类的各种实例并在需要的时候使用它们

  • Generic. With generic framework classes, you can—and must in some circumstances—create subclasses of them and override the implementations of certain methods. By subclassing them, you introduce your code into the application structure. The framework invokes the methods of your subclass at the appropriate moments.

    通用类。对于通用框架的类,你可以--在一些情况下必须--创建它们的子类,并重写一些特定方法的实现方法。通过称为它们的子类,你把你自己的代码加入到应用程序结构中。 框架在合适的时候调用你子类的各种方法。

Subclassing a generic framework class is a major technique for integrating your program-specific code into the structure provided by the frameworks. But it is not the only technique, and in many cases is not the preferred technique. As you’ll learn in a later article, the Cocoa and Cocoa Touch frameworks also include architectures and mechanisms, all based on design patterns, that enable greater cooperation and coordination between framework objects and your custom objects.

子类化一个通用框架类是整合(integrating)你的程序特定代码到框架结构中的一项主要技术。但不是唯一技术, 而且在一些情况下着也不是首选(prefered)技术。正如你在稍候的文章中所学,Cocoa 和 Cocoa Touch框架还包含了各种架构(architectures)和机制(mechanisms), 它们都基于各种设计模式,能增强框架对象跟你的自定义对象之间的合作与协调(cooperation and coordination)。

When you make a subclass, you have two basic decisions to make: which class to inherit from (the superclass) and which methods of that class to override. The following sections explore the context for making these decisions.

当你创建一个子类,你需要做两个基本决定: 从哪个类上继承(父类) 以及 重载(override)该类的哪些方法。接下来的章节探索如何做这些决定。

Inheriting from a Cocoa or Cocoa Touch Class

从Cocoa 或 Cocoa Touch 类继承

A framework such as AppKit defines a structure that, because it is generic, many types of apps can share. Because the structure is generic, it is not surprising that a few framework classes are abstract or intentionally incomplete. Such a class often implements a fair amount of common code, but leaves significant portions of the work either undone or completed in a safe default fashion.

框架比如AppKit定义了一个结构,它能让很多多种类型的应用程序共享,因为框架是通用的。 正因为结构是通用的,所以有一小部分框架中的类是抽象的或者有意的不完整也不需要惊讶。 这样的一个类通常常实现了相当数量的通用代码,但是以安全默认的方式保留了至关重要的一部分工作包括没做的或者是没完成的。

A major way to add application-specific behavior to a framework is to create a custom subclass of one of these framework classes. The subclass fills in these gaps in its superclass, supplying the pieces the framework class is missing. An instance of your custom subclass takes its place in the network of objects the framework defines and inherits from the framework the ability to work with other objects. For an app to do anything useful, it must create at least one subclass and possibly many of them.

给一个框架添加应用程序特性行为的一个主要方法就是创建这些框架类中某个类的的一个自定义子类。子类填补了父类的这些空白,提供了框架类遗失的那些部分。 你所定义(custom)的子类的实例定义在框架定义的对象网络中,并且从框架继承了跟其它对象一起工作的能力。 让一个应用程序做一个有用的事情,它必须至少创建一个子类,也可能需要多个。

The following discussion explores some of the decisions and strategies that go into subclassing and describes some of the general requirements. It does not cover in detail how to make a subclass. “Defining a Class” in The Objective-C Programming Language describes that technique.

以下的讨论探索一些进入子类的决定(decisions)和策略(strategies),同时描述了一些基本需求。 它没有覆盖所有有关如何打造(make)一个子类的细节。Objective-C 编程语言(The Objective-C Programming Language)中描述了"Defining a Class"技术。

When to Make a Subclass

何时打造一个子类

Subclassing is a process of reusing an existing class and specializing it for your needs. Sometimes all a subclass needs to do is override a single inherited method and have the method do something slightly different from the original behavior. Other subclasses might add one or two attributes to their superclass (as instance variables) and then define the methods that access and operate on these attributes, integrating them into the superclass behavior.

子类化(subclassing)是重新使用一个已经存在的类并使它专门符合你的需求的一个过程。 有时一个子类所要做的全部仅仅是重载(override)单个被继承的方法,并让该方法做一些跟原始行为稍微有所区别的事情。 其它子类也许向它们的父类添加一个或2个属性(作为实例变量),然后定义访问和操作这些属性的方法。

Subclassing starts with identifying the framework class to subclass from. Here are a few considerations to guide you:

子类化从识别子类从哪个框架类继承开始。 这里有一些参考指导:

  • Know the framework. You should become familiar with the purpose and capabilities of each class in the framework. To begin, read the introduction to a framework in the developer library and scan the list of the framework’s classes. Maybe there is a class that already does what you want to do. And if you find a class that does almost what you want to do, you’re in luck. That class is a promising superclass for your custom class.

    了解框架。 你应该熟悉框架中每个类的目标和能力。首先,阅读在开发库(developer library)里的框架说明, 然后浏览框架的类列表。 也许你已经找到一个类能完成你想要做的全部事情。如果你找到一个类能完成你想做的绝大多数事情, 你也很幸运。 那个类就有希望是你自定义类的一个父类。

    For example, when you worked through Your First Mac App, you encountered NSTextField and other classes of the AppKit framework. To find out more about these classes, you could do the following:

    举个例子,当你学习Your First Mac App时,你遇到了NSTextField 类 和 AppKit 框架中的其它类。 想要找出更多关于这些类的内容,你可以:

    1. In Xcode, choose Window > Organizer.

      在Xcode, 选择 Windoe > Organizer.

    2. Click the Documentation button in the toolbar.

      点击 工具栏里的 Documentation 按钮

    3. Click the Browse button at the top of the navigation area to begin browsing your installed developer libraries. (This button looks like an eye.)

      点击navigation area(导航区)的 浏览按钮,开始浏览你已经下载的开发者库。(该按钮看起来像一只眼睛)。

    4. Click the most recent OS X core library (you might have to log into Apple Developer first).

      The OS X Developer Library opens in the content area.

      点击 最新的 OS X 核心库(core library---你可能需要首先登陆Apple Developer(苹果开发者))。

    5. In the Documents filter field above the list of documents in the documentation area, type “AppKit Framework Reference”.

      The filtered list now shows only the name of the entered document.

      在文档区的列表上面的文档过滤项,输入“AppKit Framework Reference”。现在过滤列表仅显示跟输入内容相关的文档。

    6. Click AppKit Framework Reference to open a page that lists all the classes and protocols of AppKit.

      点击AppKit Framework Reference 打开列出AppKit框架的所有类和协议的页面。

    Read the introduction and click a listed class or protocol to learn more about it.

    阅读介绍,点击列表中的类或协议学习它的更多内容。

  • Be very clear about what your app is supposed to do. This advice applies to the app as a whole and to specific parts of the app. Some framework architectures impose their own subclassing requirements. For example, if your app is document-based, you must subclass an abstract document class.

    弄清楚你的应用程序想要做什么。 该建议适用于整个应用程序,也适用于应用程序的一个特定部分。 一些框架结构额外强加一些它们自己的子类化需求。 比如,如果你的应用程序是基于文档的,你必须子类化一个抽象文档类。

  • Define the role played by an instance of your subclass. In app development for OS X and iOS, the Model-View-Control design pattern is used to assign roles to objects. View objects appear on the user interface; model objects hold application data (and implement the algorithms that act on that data); controller objects mediate between view and model objects. Knowing what role an object plays can narrow the decision of which superclass to use. For example, if you want to do custom drawing in an OS X app, you might have to subclassNSView, the base view class in the AppKit framework.

    定义子类的一个实例要表演的角色。 在 OS X 和 iOS开发中,模型-视图-控制器(M-V-C)设计模式被用来给对象们分配角色;控制器对象在视图和模型对象之间做调解。 了解一个对象扮演什么角色能让选择哪个父类变得容易。比如,如果你想在一个OS X 应用程序里自定义绘图,你可能不得不成为NSView的子类,NSView 是AppKit 框架里的基本视图类。

Despite its importance in programming for OS X and iOS, subclassing is sometimes not the best way to solve a problem. If you just want to add a few convenience methods to a class, you might create a category instead of a subclass. Or, to inject application-specific behavior, you could employ one of the many other resources of the frameworks based on design patterns—for example, delegation. (These patterns are described in the Design Patterns article Streamline Your App with Design Patterns.) And bear in mind that some framework classes are not meant to be subclassed. The reference documentation tells you whether a framework class is meant to be subclassed.

尽管子类化在OS X 和 iOS编程里很重要,但是有时它却不是解决一个问题的最佳方法。 如果你只是想给类添加一些方便的方法, 你可能需要创建一个类别(category)代替一个子类。或者,想注入应用程序特定行为,你可以雇佣那些基于设计模式的框架中某个框架中的其它资源来完成---比如,delegation。(这些设计模式在Streamline Your App with Design Patterns里描述。) 另外,请记住有一些框架中的类是不允许被子类化的。 引用文档会告诉你该框架类能否被子类化。

Overriding a Method

重载一个方法

It’s possible to create a subclass that doesn’t reimplement any superclass methods; for example, the subclass might add additional state and define new methods that access that state and call methods of the superclass. However, for some subclasses the primary task is implementing a specific set of methods declared by a superclass (or in a protocol adopted by a superclass). Reimplementing an inherited method is known as overriding that method.

创建一个子类但是不实现任何父类的方法也是可能的;比如,子类可能添加了额外的状态,并定义了新方法来访问该状态,同时调用父类的各种方法。 然而,对于一些子类来说主要任务就是实现一个父类的特定方法集(或者在一个父类采用的一个协议里)。重新实现一个继承的方法被称为重载。

Most methods defined in a framework class are fully implemented; they exist so that you can invoke them to obtain the services the class provides. You rarely need to override such methods and shouldn’t attempt to. Other framework methods can be overridden, but there’s seldom a reason to do so.

一个框架里定义的绝大多数方法都是完全被实现的;所以你可以调用它们获得类提供的各种服务。 你很少需要去重载这样的方法,也不应该去尝试。 其它框架方法能被重载,但是也很少有理由需要这么做。

Some framework methods, however, are intended to be overridden; they exist to let you add program-specific behavior to the framework. Often the method, as implemented by the framework, does little or nothing that’s of value to your app. To give content to these kinds of methods, an app must implement its own version. The framework calls these methods at appropriate junctures in an app’s runtime life.

然而,一些框架方法是打算被重载的;它们存在就是想让你往框架里添加程序特定的行为。这些方法通常正如框架所实现的那样,对你应用程序所要完成的工作来说只做了一点或根本没做。一个应用程序必须实现它自己的方法版本才能往这些方法添加内容。在应用程序runtime生命周期中, 框架在适当的时候调用这些方法。

Invoke or Override?

The framework methods you override in a subclass won’t generally be the methods that you’ll invoke yourself, at least not directly. You simply reimplement the method and leave the rest up to the framework. In fact, the more likely you are to write an application-specific version of a method, the less likely you are to invoke it in your own code. In a general sense, a framework class declares public methods so that you, the developer, can do one of two things with them:

你在一个子类里从框架方法那重载的方法一般不是全部调用你自身的实现,至少不会直接调用你自身的实现。你简单重新实现该方法,把剩下部分留给框架实现。 事实上, 你可能更多的是实现一个方法的应用程序特定版本, 从你自己的代码里调用它可能更少。 一般来说,框架类定义公共方法,这样你或者说是开发者就能用它们完成一件或两件事情:

  • Invoke them to use the services the class provides.

    调用它们使用类提供的各种服务

  • Override them to introduce your own code into the program model defined by the framework.

    重载它们来往框架定义的程序模型里加入你自己的代码

Sometimes a method falls into both these categories; it renders a valuable service upon invocation, and it can be strategically overridden. But in most cases, if a method is one that you can invoke, it’s fully defined by the framework and doesn’t need to be redefined in your code. If the method is one that you need to reimplement in a subclass, the framework has a particular job for it to do and so will invoke the method itself at the appropriate times. This figure illustrates the two general types of framework methods.

有时一个方法会同时属于这些类别(categories);它能被调用获得有价值的服务,也能被战略性的重载。但是在大多数情况下,如果一个方法能被你调用,它就是被框架完全定义,并不需要在你的代码里被重新定义。 如果一个方法是需要你在一个子类里重新实现,则框架做了该方法的部分工作,它将在适当的时候自动调用该方法。下图显示了框架方法的2种基本类型。

 

Invoking a framework method that messages an overridden method

In this figure, a hypothetical method of your custom class (myMethodcalls the setNeedsDisplay method, which is implemented by a framework. The framework does some work to set up the environment for drawing and then calls the framework-declared method drawRect:, which is overridden by the custom class to do the actual drawing.

在上图,假设一个自定义类(myMethod)的一个方法调用了setNeedsDisplay方法, 该方法由一个框架定义。框架做了一些工作---建立了绘图的环境,然后调用框架声明的方法drawRect:,该方法被自定义类重载来完成实际绘图。

Overriding a method does not have to be a formidable task. You can often make significant change in superclass behavior by a careful reimplementation of the method that entails no more than one or two lines of code.

重载一个方法不一定是一个艰巨的任务。 你常常可以在父类行为里做重大变化,只需不超过一或两行代码对该方法做一个仔细的重新实现。

Calling the Superclass Implementation

调用父类实现

When you override a framework method, you have to decide whether to replace the behavior of the inherited method or extend or supplement that behavior. If you want to replace the existing behavior, simply provide your own implementation of the method; if you want to extend that behavior, call the superclass implementation and provide your own code.

当你重载一个框架方法,你必须决定是否要替换被继承的方法,或者扩展或者补充那个行为。 如果你想要替换存在的行为,你只要简单的提供你自己对于那个方法的实现;如果你想扩展它,你需要调用父类实现并提供你自己的代码。

You call the superclass implementation by sending the same message that invoked the method to super. By sending the message to super, you “plug in” the superclass’s code for that method into your reimplementation at the point of invocation. For example, let’s say that a hypothetical Celebrate class defines a method named performFireworks. After the framework draws and animates fireworks in a view, you want to display a banner in the view. The following figure illustrates how calling super works in this case:

使用关键字super给父类的方法实现发送一个消息就可以调用父类方法的实现。 通过给super发送消息,你在重新实现的代码顶部加入了父类的实现代码。 比如,让我们看看一个虚拟类Celebrate类定义了一个方法performFireworks. 当框架在视图上绘制和播放完烟火动画之后,你想要在视图上显示一个banner。下图显示了如何调用super,让其调用父类的实现代码。

image: ../Art/calling_super_2x.png

Thus, the decision to call super is based on how you intend to reimplement a method:

所以,调用super这个决定是基于你如何打算重新实现一个方法的基础上的:

  • If you intend to supplement the behavior of the superclass implementation, call super.

     如果你打算补充父类的实现行为,调用super。

  • If you intend to replace the behavior of the superclass implementation, don’t call super.

     如果你打算替换父类实现的行为,别调用super。

If you supplement superclass behavior, another important consideration is when to invoke the superclass implementation of a method. You might want the superclass code to do its thing before your code is executed, or vice versa.

转载于:https://www.cnblogs.com/patientAndPersist/p/3135784.html

你可能感兴趣的文章
yii2 ActiveRecord多表关联以及多表关联搜索的实现
查看>>
搜狗输入法安装--ubuntu
查看>>
ps/2接口键盘的输入及显示
查看>>
Swift———a Glance(极客学院)笔记
查看>>
【poj3294-不小于k个字符串中最长公共子串】后缀数组
查看>>
java如何获取其它用户登录的真是IP地址
查看>>
Jquery通过指定层次关系获取元素
查看>>
c# for 和 foreach 的区别
查看>>
docfx (一)
查看>>
HashMap底层实现原理/HashMap与HashTable区别/HashMap与HashSet区别
查看>>
深度学习之前馈神经网络(前向传播和误差反向传播)
查看>>
IEnumerable<T>和IQueryable<T>区别
查看>>
(转)MFC界面风格
查看>>
Centos7 tmux1.6 安装
查看>>
二叉树(三)
查看>>
linux加密文件系统 fsck 无法修复一例
查看>>
【linux配置】VMware安装Redhat6.5
查看>>
AI自主决策——有限状态机
查看>>
《http权威指南》阅读笔记(二)
查看>>
软件工程
查看>>