Tag: 协议

我对编码视图的看法

构建iOS应用程序时,可以通过多种方式创建UI。 您可以使用情节提要和Xibs或在运行时创建所有组件。 每种方法都有优点和缺点,最后,所有方法都取决于团队的目标和偏好。 但是,无论您选择什么,确保团队中的每个人都遵循相同的风格和组织非常重要。 您不希望一个庞大,混乱的情节提要或数十个没有一致模式的View Controller。 这就是为什么我尝试并创建了一个简单易用的协议来控制在所有类中创建UI组件的顺序的原因。 这远不是一个完整的框架,但是可以完成工作并且非常一致。 我称它为ViewCodable协议。 该协议仅包含按特定顺序调用的几种方法。 这是它的声明: 整个屏幕仅用几行代码创建。 例如,这是我们的ViewController声明: 我是安德烈。 一位年轻的巴西移动开发人员,喜欢与技术相关的一切。 如果您有任何疑问或建议,请随时与我联系。

Swift4 Day94:Swift开发人员的Objective-C

2018.12.26适用于Swift开发人员的Objective-C 建立String的方法 NSString * productTitle = @“弹跳球”; NSString *制造商= @“ Acme Novelty”; int float double建立方法 int数量= 144;浮动价格= 19.9;双单位价格=数量/价格; 数组的建立方法 想要把double放到Array必须先将它转成NSObject NSArray与NSDictionary是不能修改的,如果要修改要使用NSMutableDictionary [bostionDict setValue:@“巴西”为键:@“国家”]]; 是将国家的值从美国改成巴西 [bostionDict addEntriesFromDictionary:@ {@“人口”:@(656000)}]; 加新的物件到bostionDict中 switch跟for的写法跟swift没什么区别但一定要加() 新建NSObjcet档案命名为Animal后,会有h档跟m档。 .h为标头档,做为宣告属性和方法使用, .m为Objective-C档,做为实际编写属性值和方法内容使用。 先定义Animal.h的属性 枚举组{哺乳动物= 0,鸟,爬行动物,两栖动物,BonyFish,CarFish}; @ interface Animal:NSObject @ property(nonatomic,strong)NSString * name; @property(nonatomic)枚举组group; @property(nonatomic)BOOL isExtinct ; @属性(非原子)IBOutlet UIImageView * thumbnaiView; @end 建立一个为动物型别的物件称为liger 只写动物* liger; 会报错,要记得分配 […]

Swift中MVVM的面向协议的技巧

嗨伙计。 最近,MVVM已成为iOS应用程序的某种标准架构。 它提供了很好的关注点分离,格式化数据的好方法以及使用诸如RxSwift之类的框架的出色视图绑定机制。 在这篇文章中,我将提供一些技巧来简化该模式的实现。 可重用使视图变得简单 使用MVVM,视图与体系结构其余部分之间的分离非常清晰。 视图包括UIViewControllers及其出口。 实际上,实例化View变得越来越重要,特别是因为诸如Coordinator之类的模式越来越受欢迎。 在本文的其余部分中,我们将假定您正在实现这种体系结构。 Reusable是一种API,它带有对UIViews和UIViewControllers的便捷扩展,可以方便地以类型安全的方式实例化它们。 这是GitHub存储库:可重用。 它是与Carthage,CocoaPods和SPM兼容的轻量级API。 不使用它带来的幸福🖖真可惜。 基本上,Reusable提供了mixins(具有默认实现的协议),一旦您使它们符合适当的协议,它们就会向UIViews和UIViewControllers添加实例化函数。 在使用Coordinator模式时,有时需要实例化UIViewControllers并将其传递给ViewModels。 幸运的是,因为可重用在此方面有很大帮助。 这是将Reusable用于UIViewControllers实例化所需要做的事情: 为每个UIViewController创建一个Storyboard文件(当然,如果在同一个Storyboard中可能有多个UIViewController,但是为了简单起见,我们将仅考虑一个UIViewController) 将UIViewController设置为场景中的初始ViewController 创建一个UIViewController文件,其中ViewController类名与Storyboard文件名相同。 例如,如果故事板文件名为“ SettingsViewController.storyboard”,则UIViewController类将命名为“ SettingsViewController” 使UIViewController实现“ StoryboardBased”协议 就是这样。 现在,您可以使用单行代码实例化ViewController: 最酷的是, settingsViewController的类型是SettingsViewController ,不需要强制转换语句。 实际上,基于Storyboard的协议非常简单。 让我们深入了解一下: 基本上,它的作用是为实现该协议的每个UIViewController提供静态的“实例化”功能。 此函数返回UIViewController的实例。 由于“ Self”是函数的返回类型,因此类型推断可确保我们不必强制转换结果。 我强烈建议您深入研究可重用。 从类型安全的方式从Xib实例化UIView或使UITableViewCells出队时,这也将很有帮助。 面向协议的ViewModel 在当今的应用程序中,类似协调器的体系结构很常见,尤其是当与MVVM模式组合时。 这就是为什么我希望首先谈论Reusable的原因。 但是我发现有一个技巧非常有用,并且是可重用的补充。 它非常适合面向协议的方法中的MVVM模式。 这个想法不仅是为了简化UIViewControllers的实例化,而且是提供一种很好的方式来传递它们相关的ViewModels。 让我们写一个协议来定义拥有ViewModel的含义。 现在,我们可以将其与StoryboardBased混合使用,并提供一个静态函数,该函数以ViewModel作为参数实例化UIViewController。 条件扩展是一个非常强大的工具。 结合了“ StoryboardBased”和“ UIViewController”的“ where”语句使Self.instantiate函数可用,因此我们只需要将此调用包装在另一个设置UIViewController.viewModel属性的静态函数中即可。 假设我们有一个符合ViewModelBased协议的MyViewController: 使用ViewModel进行实例化将非常容易: 让我们进一步了解ViewModel抽象 到目前为止,我们仍然必须实例化ViewModel并将其提供给View。 […]

Swift协议可轻松创建可重用的基于XIB的自定义视图

在我的工作中使用了很多在Interface Builder中设计的自定义视图,我发现自己重写了相同的代码以使XIB中的视图无效。 然后,在阅读了一些文章之后,我发现协议可能是实现此目的的最佳方法(它有助于编写更少的代码)。 这里我们有协议: 使用此协议,自定义视图在被包含它的情节提要实例化时将自动从关联的XIB加载其自身的内容,而无需编写任何其他代码。 这将只是一行代码。 一种 当用作XIB的文件的所有者时,UIView子类可以符合此协议。 笔尖需要与类名称相同的名称,并且需要位于该类的束中。 如何使用: 声明您的自定义视图符合NibFileOwnerLoadable协议。 然后,您应该使用loadNibContent()覆盖init?(coder:) ,以便将其关联的XIB作为子视图加载并自动添加约束。 因此,假设您的自定义UIView子类名为SearchView,则代码将为: 最后一堂SearchView:UIView,NibFileOwnerLoadable { … 需要初始化吗?(编码器aDecoder:NSCoder){ super.init(编码器:aDecoder) loadNibContent() } } 在无法使用loadNibContent()的情况下(例如,因为您需要对子视图进行特定的配置),无论如何,您都可以使用此协议通过使用InstantiateFromNib()来仅实例化XIB的视图。 谢谢你的时间! 希望本文对您有所帮助。 在Twitter上联系: stefanofrosoni

使用协议掌握泛型:规范模式

如果您正在阅读本文,那么您很可能已经知道使用泛型的好处。 您想要减少编码。 您希望编写的代码能做更多。 您以前曾尝试在编程中使用泛型,但有可能使您从未想到的挫败感达到顶点。 你不是一个人。 能够以一种通用的方式工作,但是仍然可以成功地推断出您的类型可能很棘手。 幸运的是,将泛型与协议的使用结合起来确实很有效,而且一旦您学习了少量技术,您就会发现这棘手的事情实际上并不是那么棘手。 为了探讨该主题,我们将构建和完善一个针对以下四个方面的规范设计模式: (我希望)这些技术将成为您的编码库中的主要内容。 顺便说一句,这种模式是解决开放-封闭原则的极好方法。 我强烈建议您熟悉的东西,以及我最近 在这里 写的一些东西 。 过滤产品 我们的假设情况是,我们有一个称为Product的实体,并且我们希望能够按某种规格过滤一系列产品。 首先让我们看一下Product : 这是有道理的,因为我们的协议类型Specification是泛型的,而且我们可以可行地添加一个规范实例,该实例的关联类型不是Product 。 我们需要做的是检查items参数中的类型是否与spec参数中的类型相同。 让我们尝试一下。 技术2:检查通用实例上的条件 我们可以使用以下模式在函数声明的开头执行检查: func someFunc (参数:T)其中T.someProperty == self.someProperty 请注意,我们在输入参数之前使用了典型的占位符语法 ,以表明我们的函数正在使用泛型类型。 为了能够访问T实例的内部,我们需要首先说一下实例的类型是 ; 在这种情况下, T的类型为SomeType 。 接下来,我们需要表明我们要检查使用where关键字完成的条件。 最后,我们可以访问T.someProperty类型的属性并执行布尔检查。 现在,只要通用类型为SomeType且其值someProperty与我们自己的类型相匹配,该函数就可以使用。 考虑到这一点,让我们构建一个通用过滤器 ,该过滤器可以在规范associatedtype与物料类型匹配的情况下接受任何物料和任何规格。 现在,代替将specs参数类型设置为Specification ,我们可以改用Spec,因为它具有与我们Filter (第5行) 中的那个相关联的关联类型 ,这是安全的。 创建协议后,实现Filter本身非常简单。 我们遵循协议(第9行),设置类型别名 (第10行),然后filter(items:,specs 🙂神奇地将其自身设置为正确的类型。 现在,我们可以使用我们先前制作的Product实例进行测试 在这一点上,我们可以肯定地说一切正常。 使用我们当前的设计,创建更多的过滤器和规格是一项非常简单的任务。 但是,让我们看看是否可以进一步完善它。 目前,我们的ColorSpecification实体仅适用于Product类型的实例。 […]

Swift协议的用法-1

在上一篇文章中,我展示了使用快速扩展名进行打印的更智能方法。 并且在文章中,我敦促如果有人遇到在AnyObject上创建扩展的想法,请告知社区。 但是当我对此进行研究时,我知道这是不可能的。 但是与此同时,我很快遇到了面向协议的编程,我想可以将其用于实现我们的目标之一。 目标:我们需要避免使用与扩展方法po()相同的代码行 喜欢, 现在,使用面向协议的协议,我们可以执行以下操作, 因此,在上述类型的任何对象上都将允许使用po()。 po()的另一个优点是在同名空间中打印字典和数组,即anArrayObj.poa()或anDisctObj.pod() 今天就这些。 尝试以任何可能的方式使用扩展名,不要忘了❤️并发表评论并分享您的想法。 访问我的网站以查看到目前为止我已创建的应用程序http://www.linklyapps.in/

通过Nil-Or-Empty-Coalescing运算符(???)为空或不存在的可选项提供有意义的默认值

要解决此问题,我必须先打开可选包装,并检查它是否为nil或为空。 在这种情况下,我提供了一些有意义的默认值,例如,让用户知道他要查找的值当前不可用。 过去不久,我偶然发现了?? 运算符(顺便称为Nil合并运算符),它使您可以为nil的可选选项提供默认值。 但这不能解决可选不是null而是空的情况。 由于我不喜欢一遍又一遍地写相同的代码,只是稍微改变一下语法以反映变量名,所以我发现必须有一个更好的方法。 幸运的是,我们可以轻松扩展Optional并实现一个不错的功能来为我们做这件事。 我们只需要在扩展中编写一次解开代码,就不必再碰它了。 如果由于某种原因必须更改它,我们可以方便地在一个地方更改它,而不必经历整个项目,这确实很痛苦。 所以这里是: 那更好。 一个简单的函数,检查该值是nil还是空,并在这种情况下使用默认值。 但是,为什么我们要限制自己使用String? 使它成为各种可选功能的通用功能不是很好吗? 我认为是的,这就是为什么我更进一步。 当然,并非每个可选项都具有isEmpty属性。 字符串和数组都有它们,但是一个空的Int会是什么样子? 多数民众赞成在一个简单的解决。 我们可以使用isEmpty属性创建一个协议。 然后,我们可以限制我们的功能以查找实现上述协议的Optional。 如您所见,对于String和Array,我们甚至不需要实现某些东西,因为这些类型已经具有isEmpty属性。 现在,让我们以默认情况下没有isEmpty属性的类型实现我们的新成就,以查看它是否确实像我们期望的那样运行(我的意思是,无论如何,谁会信任计算机?) 哇,真棒。 真的行。 但是如果你像我一样,那你就是懒惰。 甚至可能是如此懒惰,以至于即使使用自动完成功能,键入“ orWhenNilOrEmpty”也已经非常费力。 当我意识到自己多么懒惰时,我想起了? 操作员。 您是否知道在Swift中可以编写自己的运算符? 当我在上面的代码上工作时,我偶然发现了这一点,这完全让我震惊。 对我来说,这是那些绝对幸运的事故之一,使我自己怀疑是否有巧合之类的事情。 这只是为了完美。 我必须立即尝试一下,这是我想到的: 我称它为“无或空”促销员,我很喜欢它。 我希望这一小部分内容可以帮助您编写更好的代码。 对我来说,这是一次很棒的学习经历。 在改进对Optional的理解的方式上(之前我从未关心过.some(wrapped)和.none,我实际上也不了解它们),我改善了对协议扩展和约束的了解,最后但并非最不重要的一点是,了解了如何编写自定义运算符。 我的建议是,每当发现自己编写相同或非常相似的代码两次以上时,就一定要研究是否存在更好的方法。

让我们谈谈协议!

面向对象编程的标志之一是继承。 但是,协议并不完全像传统继承那样,传统的继承是一个类从另一类继承而来,但是有了协议,任何给定的类,结构或枚举都可以“符合”协议。 符合协议的类或结构的实例将能够执行协议中概述的任务或指令。 根据Apple的定义,协议就像蓝图,其中包含方法,属性或定义任务所需功能的任何其他要求。 一旦创建了协议,就可以被结构,类或枚举“采用”。 在任何给定的时间,类或结构可以采用多种协议,如以下示例所示: 协议将要求类,结构或枚举的instance属性或type属性具有名称和类型。 该协议不会区分是存储属性还是计算属性。 但是,该协议将定义其仅是可获取的,还是可获取和可设置的。 如果该属性既是可获取的又是可设置的,那么它将不能作为常量存储属性或只读计算属性。 如果该属性是可获取的,那么它可以是任何类型。 这是一个示例gettable实例属性: 如前所述,协议也可以包含实例或类型方法。 这些方法的编写方式与定义任何其他实例或类型方法的方式相同。 方法也可以像属性一样具有静态前缀,在由类实现时也可以使用class或static关键字。 有时,您可能需要允许其所属实例或该实例的任何属性被修改的方法。 协议也可以具有初始化程序,它们的编写方式与类或结构初始化程序完全相同,但是它们不包含花括号或初始化程序主体。 初始化程序分为便利类或指定的初始化程序,但是当由符合该协议的类进一步定义时,必须使用“ required”修饰符 最后,类型如Int,Double或String的协议。

面向协议的Swift是否比面向对象的Swift更好?

面向协议的编程是什么意思,为什么它比OOP更好? “像我五岁一样解释”-洗衣服务示例 首先,提供的示例非常容易理解。 我强烈建议您跳过阅读评论者写的内容。 主题是“洗衣服务”。 假设有一个Laundry对象,其中封装了某些与洗衣相关的功能……“请给我洗衣服”-“好,这是您的衣服!”。 您作为客户只需说“请洗钱!”即可与Laundry互动。 Laundry对象开始工作并执行其工作,其范围可能从简单到令人难以置信的复杂–美丽之处在于,作为客户,就像需要洗衣服的人一样,您不在乎。 只要洗完衣服就可以退回衣服,生活就很棒! 面向对象的“问题” 在构建软件时,我们是在使用其他人构建的代码,还是创建供他人使用的代码,不是吗? 我们正在使用的代码“挂钩”到其他开发人员设计并提供给我们的东西,或者我们正在创建其他代码将“挂钩”并与之交互的代码,即使“其他代码”是由我们在自己的应用程序中。 在成为代码的客户和创建者时,我们会同时戴上两顶帽子。 但是,如果我们将Laundry对象作为开发人员/创建者 ,而不是作为客户端 (即需要洗衣服的人)来工作,该怎么办? 如果我们作为开发人员将一个Laundry对象交给了一个库,并且想要自定义它的行为,那么……可能会提高launderClothes()的性能,或者重写它的实现以使用一些令人惊奇的新洗衣服务。 我们这样做的方法是创建一个子类 。 评论者说,这是具有对象定向的牛肉: [Object Orientation]通过继承来公开状态和内部,从而鼓励“封装复杂性”。 解说:软件具有天生的复杂性。 对象是封装这种复杂性的“事物”。 但是,他们以某种方式做到这一点:他们公开了某些状态和功能。 这些关于复杂性的抽象通过系统传播和定制的方式就是通过称为继承的机制。 但是评论者称这种方法是“麻烦的”。 为什么? 好… “我可能不想知道我的干洗是如何完成的,但是如果我想设计一条从脏衣服到干净衣服的更好方法,我就必须知道所执行步骤的每一个最后细节,这样我才能尝试在我的子类中完善它们。” 因此,评论者从开发人员/创建者的角度出发。 需要指出的是,要真正能够改善子类中的性能或优化算法,我们必须要知道在超类中执行的步骤的每个细节。 我们并非总是可以发现超类实现来改进它的情况。 转向协议方向 那么…协议方向? 如果更好,那会更好吗? 我喜欢评论者以洗衣服务的面向对象示例为例,并从协议而非对象的角度出发细化了细微差别。 真。 看一看。 我们看到的主要区别是,与其拥有一个Laundry对象而不是一个以自己的特定方式进行Laundry对象,而是发生了转变:我们开始着手描述完成洗衣的方式 。 如果我想由一个特定的人以一种特定的方式来完成洗衣, 那么我会去面向对象的,而不再关心事情如何完成。 但是,如果我想概括一下洗衣服的方法 ,则需要以协议为导向,并不再关心其他所有事情。 在协议定向中,唯一重要的是接口 ……客户端将与之交互的事物。 尽最大可能通过一个协议来描述它,然后让其他事情出现并担心该如何做 。 最后,需要洗衣服的人唯一需要知道的是他们可以使用哪些界面来完成他们需要完成的洗涤。 能够坐下来思考一下,如果您从图片中删除了状态和继承,并且只考虑了与该特定任务的最低要求接口,将会看起来如何,这是一种更强大,更简单的编程方法,使重用比OO曾经做到过。 外卖 对我来说,这个关于Protocol Orientation的要点是:Protocols是泛化的 。 […]

协议可比较

平等。 字符串,双精度字,字符串和双精度整数,操作员binario == queharáel trabajo requerido。 Ejemplo: 佩罗·奎·帕萨(Pero¿) 请参见“ 编译器必填项: 二进制运算符’==’不能应用于两个’Cliente’操作数 ”。 德阿库多:是的! 没有幻想,迷惑不解。 符合基本协议的协议。 啊! 否否客户端1 ==客户端2,则没有问题(客户端!),请不要在客户端上使用sapro。 不能完全扩展的功能 。 客户可以在“任何客户使用”上查看“客户身份”,“客户身份”和“客户身份” 。 重要事项:协议的可食用性,等价的海,等价物,反射性的cumpla con laspropiedade,simetría和transivividad。 从整体上了解客户的需求。 Reflexibidad :cliente_ A == cliente_ A Simetría 。 cliente_ A == cliente_ B 隐含 cliente_ B == cliente_ A Transitividad 。 cliente_ A == cliente_ B && clienteB == […]