当前位置: 首页 > news >正文

济南市建设工程招标投标协会网站ps做网站页面步骤

济南市建设工程招标投标协会网站,ps做网站页面步骤,dw个人简历网页制作代码,企业展示型网站有哪些Combine 系列 Swift Combine 从入门到精通一Swift Combine 发布者订阅者操作者 从入门到精通二Swift Combine 管道 从入门到精通三Swift Combine 发布者publisher的生命周期 从入门到精通四Swift Combine 操作符operations和Subjects发布者的生命周期 从入门到精通五Swift Com…Combine 系列 Swift Combine 从入门到精通一Swift Combine 发布者订阅者操作者 从入门到精通二Swift Combine 管道 从入门到精通三Swift Combine 发布者publisher的生命周期 从入门到精通四Swift Combine 操作符operations和Subjects发布者的生命周期 从入门到精通五Swift Combine 订阅者Subscriber的生命周期 从入门到精通六Swift 使用 Combine 进行开发 从入门到精通七Swift 使用 Combine 管道和线程进行开发 从入门到精通八Swift Combine 使用 sink, assign 创建一个订阅者 从入门到精通九Swift Combine 使用 dataTaskPublisher 发起网络请求 从入门到精通十Swift Combine 用 Future 来封装异步请求 从入门到精通十一Swift Combine 有序的异步操作 从入门到精通十二Swift Combine 使用 flatMap 和 catch错误处理 从入门到精通十三Swift Combine 网络受限时从备用 URL 请求数据 从入门到精通十四Swift Combine 通过用户输入更新声明式 UI 从入门到精通十五 1. 级联多个 UI 更新包括网络请求 目的: 由上游的订阅者触发多个 UI 元素更新 以下提供的示例是扩展了 通过用户输入更新声明式 UI 例子中的发布者, 添加了额外的 Combine 管道当有人与所提供的界面交互时以更新多个 UI 元素。 此视图的模式从接受用户输入的文本框开始紧接着是一系列操作事件流 使用一个 IBAction 来更新 Published username 变量。我们有一个订阅者usernameSubscriber连接到 $username 发布者该发布者发送值的更新并尝试取回 GitHub user。 结果返回的变量 githubUserData也被 Published 标记是一个 GitHub 用户对象的列表。 尽管我们只期望在这里获得单个值但我们使用列表是因为我们可以方便地在失败情况下返回空列表无法访问 API 或用户名未在 GitHub 注册。我们有 passthroughSubject networkActivityPublisher 来反映 GithubAPI 对象何时开始或完成网络请求。我们有另一个订阅者 repositoryCountSubscriber 连接到 $githubUserData 发布者该发布者从 github 用户数据对象中提取出仓库个数并将其分配给要显示的文本字段。我们有一个最终的订阅者 avatarViewSubscriber 连接到 $githubUserData尝试取回与用户的头像相关的图像进行显示。 返回空列表很有用因为当提供无效的用户名时我们希望明确地移除以前显示的任何头像。 为此我们需要管道始终有值可以流动以便触发进一步的管道和相关的 UI 界面更新。 如果我们使用可选的 String? 而不是 String[] 数组可选的字符串不会在值是 nil 时触发某些管道并且我们始终希望管道返回一个结果值即使是空值。 以 assign 和 sink 创建的订阅者被存储在 ViewController 实例的 AnyCancellable 变量中。 由于它们是在类实例中定义的Swift 编译器创建的 deinitializers 会在类被销毁时取消并清理发布者。 许多喜欢 RxSwift 的开发者使用的是 “CancelBag” 对象来存储可取消的引用并在销毁时取消管道。 可以在这儿看到一个这样的例子https://github.com/tailec/CombineExamples/blob/master/CombineExamples/Shared/CancellableBag.swift. 这与 Combine 中在 AnyCancellable 类型上调用 store 函数是相似的它允许你将订阅者的引用保存在一个集合中例如 SetAnyCancellable。 管道使用 subscribe 操作符明确配置为在后台队列中工作。 如果没有该额外的配置管道将被在主线程调用并执行因为它们是从 UI 线程上调用的这可能会导致用户界面响应速度明显减慢。 同样当管道的结果分配给或更新 UI 元素时receive 操作符用于将该工作转移回主线程。 为了让 UI 在 Published 属性发送的更改事件中不断更新我们希望确保任何配置的管道都具有 Never 的失败类型。 这是 assign 操作符所必需的。 当使用 sink 操作符时它也是一个潜在的 bug 来源。 如果来自 Published 变量的管道以一个接受 Error 失败类型的 sink 结束如果发生错误sink 将给管道发送终止信号。 这将停止管道的任何进一步处理即使有变量仍然被更新。 UIKit-Combine/GithubAPI.swift import Foundation import Combineenum APIFailureCondition: Error {case invalidServerResponse }struct GithubAPIUser: Decodable { // 1// A very *small* subset of the content available about// a github API user for example:// https://api.github.com/users/heckjlet login: Stringlet public_repos: Intlet avatar_url: String }struct GithubAPI { // 2// NOTE(heckj): Ive also seen this kind of API access// object set up with with a class and static methods on the class.// I dont know that theres a specific benefit to making this a value// type/struct with a function on it./// externally accessible publisher that indicates that network activity is happening in the API proxystatic let networkActivityPublisher PassthroughSubjectBool, Never() // 3/// creates a one-shot publisher that provides a GithubAPI User/// object as the end result. This method was specifically designed to/// return a list of 1 object, as opposed to the object itself to make/// it easier to distinguish a no user result (empty list)/// representation that could be dealt with more easily in a Combine/// pipeline than an optional value. The expected return type is a/// Publisher that returns either an empty list, or a list of one/// GithubAPUser, with a failure return type of Never, so its/// suitable for recurring pipeline updates working with a Published/// data source./// - Parameter username: username to be retrieved from the Github APIstatic func retrieveGithubUser(username: String) - AnyPublisher[GithubAPIUser], Never { // 4if username.count 3 { // 5return Just([]).eraseToAnyPublisher()}let assembledURL String(https://api.github.com/users/\(username))let publisher URLSession.shared.dataTaskPublisher(for: URL(string: assembledURL)!).handleEvents(receiveSubscription: { _ in // 6networkActivityPublisher.send(true)}, receiveCompletion: { _ innetworkActivityPublisher.send(false)}, receiveCancel: {networkActivityPublisher.send(false)}).tryMap { data, response - Data in // 7guard let httpResponse response as? HTTPURLResponse,httpResponse.statusCode 200 else {throw APIFailureCondition.invalidServerResponse}return data}.decode(type: GithubAPIUser.self, decoder: JSONDecoder()) // 8.map {[$0] // 9 }.catch { err in // 10// When I originally wrote this method, I was returning// a GithubAPIUser? optional.// I ended up converting this to return an empty// list as the error output replacement so that I could// represent that the current value requested didnt *have* a// correct github API response.return Just([])}.eraseToAnyPublisher() // 11return publisher} }此处创建的 decodable 结构体是从 GitHub API 返回的数据的一部分。 在由 decode 操作符处理时任何未在结构体中定义的字段都将被简单地忽略。与 GitHub API 交互的代码被放在一个独立的结构体中我习惯于将其放在一个单独的文件中。 API 结构体中的函数返回一个发布者然后与 ViewController 中的其他管道进行混合合并。该结构体还使用 passthroughSubject 暴露了一个发布者使用布尔值以在发送网络请求时反映其状态。我最开始创建了一个管道以返回一个可选的 GithubAPIUser 实例但发现没有一种方便的方法来在失败条件下传递 “nil” 或空对象。 然后我修改了代码以返回一个列表即使只需要一个实例它却能更方便地表示一个“空”对象。 这对于想要在对 GithubAPIUser 对象不再存在后在后续管道中做出响应以擦除现有值的情况很重要 —— 这时可以删除 repositoryCount 和用户头像的数据。这里的逻辑只是为了防止无关的网络请求如果请求的用户名少于 3 个字符则返回空结果。handleEvents 操作符是我们触发网络请求发布者更新的方式。 我们定义了在订阅和终结完成和取消时触发的闭包它们会在 passthroughSubject 上调用 send()。 这是我们如何作为单独的发布者提供有关管道操作的元数据的示例。tryMap 添加了对来自 github 的 API 响应的额外检查以将来自 API 的不是有效用户实例的正确响应转换为管道失败条件。decode 从响应中获取数据并将其解码为 GithubAPIUser 的单个实例。map 用于获取单个实例并将其转换为单元素的列表将类型更改为 GithubAPIUser 的列表[GithubAPIUser]。catch 运算符捕获此管道中的错误条件并在失败时返回一个空列表同时还将失败类型转换为 Never。eraseToAnyPublisher 抹去链式操作符的复杂类型并将整个管道暴露为 AnyPublisher 的一个实例。 2. UIKit-Combine/GithubViewController.swift import UIKit import Combineclass ViewController: UIViewController {IBOutlet weak var github_id_entry: UITextField!IBOutlet weak var activityIndicator: UIActivityIndicatorView!IBOutlet weak var repositoryCountLabel: UILabel!IBOutlet weak var githubAvatarImageView: UIImageView!var repositoryCountSubscriber: AnyCancellable?var avatarViewSubscriber: AnyCancellable?var usernameSubscriber: AnyCancellable?var headingSubscriber: AnyCancellable?var apiNetworkActivitySubscriber: AnyCancellable?// username from the github_id_entry field, updated via IBActionPublished var username: String // github user retrieved from the API publisher. As its updated, it// is wired to update UI elementsPublished private var githubUserData: [GithubAPIUser] []// publisher reference for this is $username, of type String, Nevervar myBackgroundQueue: DispatchQueue DispatchQueue(label: viewControllerBackgroundQueue)let coreLocationProxy LocationHeadingProxy()// MARK - ActionsIBAction func githubIdChanged(_ sender: UITextField) {username sender.text ?? print(Set username to , username)}// MARK - lifecycle methodsoverride func viewDidLoad() {super.viewDidLoad()// Do any additional setup after loading the view.let apiActivitySub GithubAPI.networkActivityPublisher // 1.receive(on: RunLoop.main).sink { doingSomethingNow inif (doingSomethingNow) {self.activityIndicator.startAnimating()} else {self.activityIndicator.stopAnimating()}}apiNetworkActivitySubscriber AnyCancellable(apiActivitySub)usernameSubscriber $username // 2.throttle(for: 0.5, scheduler: myBackgroundQueue, latest: true)// ^^ scheduler myBackGroundQueue publishes resulting elements// into that queue, resulting on this processing moving off the// main runloop..removeDuplicates().print(username pipeline: ) // debugging output for pipeline.map { username - AnyPublisher[GithubAPIUser], Never inreturn GithubAPI.retrieveGithubUser(username: username)}// ^^ type returned in the pipeline is a Publisher, so we use// switchToLatest to flatten the values out of that// pipeline to return down the chain, rather than returning a// publisher down the pipeline..switchToLatest()// using a sink to get the results from the API search lets us// get not only the user, but also any errors attempting to get it..receive(on: RunLoop.main).assign(to: \.githubUserData, on: self)// using .assign() on the other hand (which returns an// AnyCancellable) *DOES* require a Failure type of NeverrepositoryCountSubscriber $githubUserData // 3.print(github user data: ).map { userData - String inif let firstUser userData.first {return String(firstUser.public_repos)}return unknown}.receive(on: RunLoop.main).assign(to: \.text, on: repositoryCountLabel)let avatarViewSub $githubUserData // 4.map { userData - AnyPublisherUIImage, Never inguard let firstUser userData.first else {// my placeholder data being returned below is an empty// UIImage() instance, which simply clears the display.// Your use case may be better served with an explicit// placeholder image in the event of this error condition.return Just(UIImage()).eraseToAnyPublisher()}return URLSession.shared.dataTaskPublisher(for: URL(string: firstUser.avatar_url)!)// ^^ this hands back (Data, response) objects.handleEvents(receiveSubscription: { _ inDispatchQueue.main.async {self.activityIndicator.startAnimating()}}, receiveCompletion: { _ inDispatchQueue.main.async {self.activityIndicator.stopAnimating()}}, receiveCancel: {DispatchQueue.main.async {self.activityIndicator.stopAnimating()}}).receive(on: self.myBackgroundQueue)// ^^ do this work on a background Queue so we dont impact// UI responsiveness.map { $0.data }// ^^ pare down to just the Data object.map { UIImage(data: $0)!}// ^^ convert Data into a UIImage with its initializer.catch { err inreturn Just(UIImage())}// ^^ deal the failure scenario and return my replacement// image for when an avatar image either isnt available or// fails somewhere in the pipeline here..eraseToAnyPublisher()// ^^ match the return type here to the return type defined// in the .map() wrapping this because otherwise the return// type would be terribly complex nested set of generics.}.switchToLatest()// ^^ Take the returned publisher thats been passed down the chain// and subscribe it out to the value within in, and then pass// that further down..receive(on: RunLoop.main)// ^^ and then switch to receive and process the data on the main// queue since were messing with the UI.map { image - UIImage? inimage}// ^^ this converts from the type UIImage to the type UIImage?// which is key to making it work correctly with the .assign()// operator, which must map the type *exactly*.assign(to: \.image, on: self.githubAvatarImageView)// convert the .sink to an AnyCancellable object that we have// referenced from the implied initializersavatarViewSubscriber AnyCancellable(avatarViewSub)// KVO publisher of UIKit interface elementlet _ repositoryCountLabel.publisher(for: \.text) // 5.sink { someValue inprint(repositoryCountLabel Updated to \(String(describing: someValue)))}}}我们向我们之前的 controller 添加一个订阅者它将来自 GithubAPI 对象的活跃状态的通知连接到我们的 activityIndicator。从 IBAction 更新用户名的地方来自我们之前的示例 通过用户输入更新声明式 UI我们让订阅者发出网络请求并将结果放入一个我们的 ViewController 的新变量中还是 Published。第一个订阅者连接在发布者 $githubUserData 上。 此管道提取用户仓库的个数并更新到 UILabel 实例上。 当列表为空时管道中间有一些逻辑来返回字符串 “unknown”。第二个订阅者也连接到发布者 $githubUserData。 这会触发网络请求以获取 github 头像的图像数据。 这是一个更复杂的管道从 githubUser 中提取数据组装一个 URL然后请求它。 我们也使用 handleEvents 操作符来触发对我们视图中的 activityIndi​​cator 的更新。 我们使用 receive 在后台队列上发出请求然后将结果传递回主线程以更新 UI 元素。 catch 和失败处理在失败时返回一个空的 UIImage 实例。最终订阅者连接到 UILabel 自身。 任何来自 Foundation 的 Key-Value Observable 对象都可以产生一个发布者。 在此示例中我们附加了一个发布者该发布者触发 UI 元素已更新的打印语句。 虽然我们可以在更新 UI 元素时简单地将管道连接到它们但这使得和实际的 UI 元素本身耦合更紧密。 虽然简单而直接但创建明确的状态以及分别对用户行为和数据做出更新是一个好的建议这更利于调试和理解。 在上面的示例中我们使用两个 Published 属性来保存与当前视图关联的状态。 其中一个由 IBAction 更新第二个使用 Combine 发布者管道以声明的方式更新。 所有其他的 UI 元素都依赖这些属性的发布者更新时进行更新。 3. 运行结果 json from https://api.github.com/users/zgpeace {login: zgpeace,id: 2386257,node_id: MDQ6VXNlcjIzODYyNTc,avatar_url: https://avatars.githubusercontent.com/u/2386257?v4,gravatar_id: ,url: https://api.github.com/users/zgpeace,html_url: https://github.com/zgpeace,followers_url: https://api.github.com/users/zgpeace/followers,following_url: https://api.github.com/users/zgpeace/following{/other_user},gists_url: https://api.github.com/users/zgpeace/gists{/gist_id},starred_url: https://api.github.com/users/zgpeace/starred{/owner}{/repo},subscriptions_url: https://api.github.com/users/zgpeace/subscriptions,organizations_url: https://api.github.com/users/zgpeace/orgs,repos_url: https://api.github.com/users/zgpeace/repos,events_url: https://api.github.com/users/zgpeace/events{/privacy},received_events_url: https://api.github.com/users/zgpeace/received_events,type: User,site_admin: false,name: zgpeace,company: HSBC,blog: https://blog.csdn.net/zgpeace,location: guangzhou,email: null,hireable: null,bio: AI, CNN, AutoDrive, Architect, Full Stack Developer\r\n\r\nEver work in Alibaba,twitter_username: zgpeace,public_repos: 138,public_gists: 5,followers: 12,following: 12,created_at: 2012-09-20T13:55:28Z,updated_at: 2023-12-27T06:44:33Z }参考 https://heckj.github.io/swiftui-notes/index_zh-CN.html 代码 https://github.com/heckj/swiftui-notes
http://www.pierceye.com/news/74384/

相关文章:

  • 长沙17个片区城市更新海南网站优化公司
  • 上海网站建设优化价格外贸商城网站系统
  • 东莞石龙网站建设定制黄冈网站建设营销
  • 唐山做企业网站手游推广平台
  • 中山网站建设设计wordpress know how
  • 素材网站 国外计算机 网站开发 文章
  • 新乡网站建设制作东莞关键词优化免费诊断
  • 设置网站关键词怎么做粤信签微信小程序是什么
  • 高端营销网站建设凡客官网 电脑版
  • 怎么申请网站空间域名怎么做网站网站的代理
  • 网站页面布局模板centos7 wordpress搭建
  • 江苏建设人才网站做网站如何排版
  • php mysql网站开发试题ac2c十大平台
  • 网页小游戏推荐东莞网站seo方法
  • wordpress 关闭网站绍兴公司网站制作公司
  • 哪个网站有免费ppt下载中国新闻社总编辑
  • 青岛学网站建设的大学天猫购物商城
  • 学校网站开发分析报告wordpress 无法安装
  • 网站建设行业的分析微信小程序官网登陆
  • wordpress迁移站点上海建设网站方法
  • 网站推广销售莱芜网站建设开发公司
  • vue.js2.5 pc网站开发佛山seo整站优化
  • 2003访问网站提示输入用户名密码wordpress+qq音乐插件
  • 北京企业响应式网站建设wordpress如何给头部加个搜索
  • 衡阳县做淘宝网站建设七种人不宜学软件工程
  • 为什么做不了自己的网站发视频的网址网址是什么?
  • 创新的购物网站建设wordpress默认密码
  • 现代郑州网站建设网页设计介绍北京网站
  • 哪网站建设好王晴儿网站建设
  • 贵州飞乐云毕节网站建设国外的做的比较优秀的网站有哪些