首页 文章 精选 留言 我的

精选列表

搜索[接触动力学],共6821篇文章
优秀的个人博客,低调大师

初次上手接触ArkTs

本文分享自华为云社区《学习ArtTs -- 初见ArkTs》,作者:Uncle_Tom。 1. 前言 需要静态分析去检查一个语言,必须对这个语言有深刻的认识,才能有效的对这个语言进行有效的检查。 我常说:“作为一个程序分析员需要比一般的程序员考虑的更多。通常程序员只要考虑在需求和结果之间建立一条通道就可以了完成任务了。但程序分析员需要考虑在需求和结果之间的各种通道的可能性,并对他们做出条件判断,否则漏报和误报会始终伴着你。随着规则的增多,你会陷入没有全景而导致的巨量维护工作中,无法自拔,耗尽你最后一丝热情。” 孙子曰:知彼知己者,百战不殆;不知彼而知己,一胜一负,不知彼,不知己,每战必殆。 摘自《 孙子兵法·谋攻篇 》 新年伊始,万象更新。需要支撑鸿蒙的主要开发语言之一的 ArtTs。已不知这是我要学习的第几个语言了。这是一个怎样的语言? 充满了对未知的好奇。 外面阳光格外的明媚,手机里不断翻唱着老歌,You can hear the whistle blow a hundred miles,a hundred miles, a hundred miles … 这样的环境正适合看点东西,要不看下 – ArtTs。 2. 找到 ArtTs 起点 从 Edge 里查找: “鸿蒙开发语言”,不难找到: 点入链接:https://developer.harmonyos.com/cn/docs/documentation/doc-guides-V3/arkts-get-started-0000001504769321-V3 显示: 从左边导航条看,涵盖了初学者需要的基本信息目录:快速入门、语言学习、开发、工具、测试、术语。文档结构完整,不错。 页面上面的一行淡黄色的小字,告诉我们这个文档是鸿蒙 3.1/4.0 共用的。这也让我注意到文档边上的版本下拉框: 都说鸿蒙 4.0 之后将不再支持 Android,里面会是什么样的?尽管已经登录了华为云账号,但仍然显示需要授权账户,也未说明在哪里可以申请,看来 NEXT 版本还没有对外公开。 无他,回到 3.1/4.0 继续。 3. 快速入门 3.1. 开发准备 我是小白,从头开始。按导航从头开始,进入“开发准备”。 以一个简单的例子开始,是快速入门的通用做法,能够让学习者快速带入。 作者的目的是想通过这个例子让学习者能够了解快速鸿蒙应用的开发流程。 例子需求 这个例子涵盖了两个简单的页面: 页面一显示“Hello World”。字体:加粗,字号:xx;一个淡蓝色“Next”按键。 页面二显示“Hi there”。字体:加粗,字号:xx;同页面一字体设置;注:原文翻译过来“hi 那里”,这里的there 感觉怪怪的。这里用“Hi,I am here”似乎更有对话感。一个淡蓝色“Back”按键。风格同页面一按键设置。 页面交互页面一按下“Next”后,页面跳转到页面二;页面二按下“Back”后,页面跳转回页面一。 这里有几个疑问 鸿蒙的UI框架是怎样的?和我们常用的 node.js 有什么差别?再学习成本高么? 页面里面事件驱动的机制是怎样的?前后台的交互和 Android 有什么不同?实现上支持哪些事件处理机制? 客户端会缓存最近浏览的页面么?缓存的机制是怎样的?当缓存页面的信息有变动时,会不会同步刷新? 先放下这些疑问,往下看。 3.2. 基本概念 3.2.1. UI 框架 这里的UI开发框架称为:方舟开发框架(ArkUI框架),同样提供了 UI 所须要的:基本组件、布局计算、动画能力、UI交互、绘制等。 但这里针对不同的目的和开发者提供了两种不同的开发范式。 类Web开发范式 一种应该是大家比较熟悉的开发范式,这里被称为 “类Web开发范式”,使用 JS 语言,但从适用场景和适用人群来看,这个范式似乎只是一个初级的开发,整个应用较为简单。 声明式开发范式 这里用了一个词“声明式”, 这个词是从程序语言里得到的。 我们知道程序语言有两种,命令式(Imperative)和声明式(Declarative)。 我们常用的开发语言,例如C,Java,Python等都是属于命令式语言,和名字一样,我们需要通过程序告诉计算机每一步该怎么做,然后得到输出结果。 我们也同样熟悉声明式语言的典型代表 – SQL。我们知道 SQL 并不需要我们告诉计算机怎么做,而是只要告诉我们需要结果的特征或条件,就能得到查询结果,至于计算机怎么得到这个结果,我们并不需要关心数据库底层复杂的实现逻辑。 例如:我们要查找 userid = 1 的用户名和年纪,以及他的朋友的名字 这里有两张表: 用户表(user):id,name,age,等等; 关系表(relation):relationId,userId,relation,name,等等。 select u.name,u.age,f.name from user u, relation r where u.id=1 and u.id = r.userid and r.relation ='friend' Facebook 使用 GraphQL 和 Relay 重构了 Facebook 的网站。这也让我们看到了前端的另一种构建方式。这里的GraphQL 同样是一种声明式语言。 上面的SQL 例子用 GraphQL来写就变成了下面的代码 { user(id: 1) { name age friends { name } } } 至于 ArkTs 怎样通过声明式的开发范式,简化 UI 的开发,我们继续往下看,又挖一坑,嘿嘿… 。 3.2.2. 应用模型 应用模型是我们连接前端和后端的重要的组成部分。我们从早先的 MVC(Model View Controller), MVP(Model-View-Presenter) 模型,逐步过度到了 MVVM(Model-View-ViewModel) 模型。 MVVM 模型。 MVVM 本质是 MVC 模式的进一步解耦,它通过将 UI 逻辑从 View 中分离出来,将数据处理逻辑从 View 和 Model 中分离出来,使得每个组件的职责更加明确,代码更易于组织和维护。ViewModel 充当着 View 和 Model 之间的桥梁,负责将 Model 中的数据转换成 View 可用的形式,并且通过数据绑定将数据自动同步到 View 上。这种双向绑定使得 UI 的更新变得自动化,开发者只需要专注于数据的处理和业务逻辑的编写,而无需过多关心UI的更新。 MVVM 模式有助于将应用程序的业务和表示逻辑与用户界面 (UI) 清晰分离。 保持应用程序逻辑和 UI 之间的清晰分离有助于解决许多开发问题,并使应用程序更易于测试、维护和演变。 它还可以显著提高代码重用机会,并允许开发人员和 UI 设计人员在开发应用各自的部分时更轻松地进行协作。 Stage 模型 文中提到了两个模型:FA(Feature Ability)模型 和 Stage 模型。 FA 模型已经被废弃,就不看了。Stage 模型是什么? 文中没有给出 stage 的具体含义,也没给出起名的说明。 从下面 Stage 模型的设计目标,我们可以对 stage 模型有个初步认识。 为复杂应用而设计 多个应用组件共享同一个ArkTS引擎(运行ArkTS语言的虚拟机)实例,应用组件之间可以方便的共享对象和状态,同时减少复杂应用运行对内存的占用。 采用面向对象的开发方式,使得复杂应用代码可读性高、易维护性好、可扩展性强。 支持多设备和多窗口形态 应用组件管理和窗口管理在架构层面解耦:便于系统对应用组件进行裁剪(无屏设备可裁剪窗口);便于系统扩展窗口形态;在多设备(如桌面设备和移动设备)上,应用组件可使用同一套生命周期。 平衡应用能力和系统管控成本,Stage模型重新定义应用能力的边界,平衡应用能力和系统管控成本。提供特定场景(如卡片、输入法)的应用组件,以便满足更多的使用场景;规范化后台进程管理:为保障用户体验,Stage模型对后台应用进程进行了有序治理,应用程序不能随意驻留在后台,同时应用后台行为受到严格管理,防止恶意应用行为。 3.3. 工具 这里有个新的工具 DevEco Stuido。从介绍看是个一站式的开发平台:面向全场景多设备,提供一站式的分布式应用开发平台,支持分布式多端开发、分布式多端调测、多端模拟仿真,全方位的质量与安全保障。 先下载试用。 下载 devecostudio-windows-3.1.0.501.zip 后, 本以为是个直接使用版本,结果还是个 exe 安装版本,看来可能还是需要在 windows 系统里注册一些服务。 安装完了立刻卡壳了。node.js 本地版本是符合要求的,可还是给出了错误提示。 一时无解。只好今天先到这里了。 参考 HarmonyOS Developer 微软: 模型-视图-视图模型 (MVVM) 点击关注,第一时间了解华为云新鲜技术~

优秀的个人博客,低调大师

App Inventor for Android初接触

今天收到了App Inventor for Android的注册确认信,可以用我的Gmail来登录App Inventor了。于是,按照手册做了几个小例子。App Inventor使用起来时非常方面的,省去了很多的编程,可以快速的构建应用程序。不过现在App Inventor还是有很多的限制的,比如只能构建单页面的程序、不适合构建复杂的应用程序等。 在Designer中设计界面。 Designer被分为4部分:Viewer编辑组件、Palette显示所有可用的组件、Components List显示了所有的组件和上传的图片声音等资源、Properties属性的设置。 通过拖放的方式摆放组件,在属性中设置其相应的属性就可以了: 在Blocks Editor中编辑事件的处理: 在Blocks Editor中的My Blocks中列出了所有已经添加的组件: 点击相应的组件,即出现与该组件相应的事件,如点击Button1出现下述的列表: 示例程序对上述列表给出了一个说明: l when ... do ... blocks define event handlers, that tell components what to do when something happens. l call ... blocks tell components to do things. 点击Blocks Editor空白处会出现下面的列表,可用使用这些实现逻辑控制、参数设置等功能。 最终完成的Blocks如下: 打电话的实现 PhoneNumberPicker可以从通讯录中提取联系人的信息 PhoneCall用来拨打电话 Canvas 拖放一个Canvas组件到Viewer中,对其Touched事件(点触)和Dragged事件(拖曳)进行处理。 Blocks: 布局管理 App Inventor提供了三种布局,使用的时候设置好属性,把组件拖到上面即可。 程序的打包 在设计器中,通过Package for Phone可以实现程序的打包,包括下载到手机和下载到电脑。 本文转自feisky博客园博客,原文链接:http://www.cnblogs.com/feisky/archive/2010/08/14/1799504.html,如需转载请自行联系原作者

优秀的个人博客,低调大师

Kotlin最初接触时碰的坑

kotlin调用ButterKnife (gradle更新后,ButterKnife不再支持,Kotlin使用的库KotterKnife等待发布) (KotterKnife:https://github.com/JakeWharton/kotterknife) // app/build.gradle中添加相关配置引入ButterKnifer dependencies { implementation 'com.jakewharton:butterknife:8.8.1' kapt 'com.jakewharton:butterknife-compiler:8.8.1' } // kotlin中添加相关注解方式如下 @BindView(R.id.xxxxxx) lateinit var view:View // 同java,使用注解 ButterKnife.bind(this) // activity为例,其它类比java kotlin多重嵌套向上调用 class A { private var m:Int = 0 inner class B { private var m:Int = 1 inner class C { private var m:Int = 2 fun callFunc{ this.m // 2 this@B.m // 1 this@A.m // 0 } } } } // 关键字inner,内部类没有加inner前缀,多重内部类无法向上调用 // 适用于隐形内部类 kotlin隐形创建接口对象时,提示没有构造函数的问题。no construct // 错误示例 interface iFace{ ..... } var fc = iFace{....} // interface iFace does not have constructors // 使用方法 interface iFace{ ..... } var fc = object : iFace{....} // interface iFace does not have constructors kotlin使用mutablelist可写列表 与java不同,kotlin分为只读列表List和可读写列表MutableList var readOnlyList : List<T> = emptyList() var readOnlyList : List<T> = listOf(t1, t2, t3, t4) // 只读列表 var readWriteList : MutableList<T> = mutableListof() // 可读写列表 var readWriteList : MutableList<T> = mutableListOf<T>() 坑列表会持续更新。。。。

优秀的个人博客,低调大师

与oom-killer的亲密接触

10月11日晚上,云平台安排上线。需要通宵工作,这次版本更新的重头戏是需要把一个新的模块部署到线上环境,这个新的模块叫prxdms,用来替换掉原有的dms。 我作为一个涉世未深的运维小青年,就按照部署文档按步骤操作,把新版的prxdmx文件复制粘贴,进程开启,然后把老的dms进程断开,检查进程之后,就去厕所里痛痛快快的释放了一下膀胱括约肌的压力,怒来一泡尿,盘算着如何在剩下的时间里刷刷论坛微博,打打酱油然后回家睡觉。 就在我吹着口哨返回到办公室里,他们却齐齐的瞅我,然后告诉我,线上的设备大面积掉线,后来#ps -ef|grep prxdms一下发现是prxdms没有进程,一致怀疑我是困傻了,没有启动prxdms。 我是很相信我自己的,而且翻阅history也证明了我没有犯低级错误,但是很奇怪,我明明启动了prxdms进程,为什么会自己跳出呢? 查看prxdms自己的日志,无果,只提示断开,没有显示断开原因。然后重新启动prxdms,top一下,果然内存和cpu的数字令人发指,但是新进程启动都会有这么一个过程,然后会慢慢地下降。但是好景没多久,再一次集体进程跳出。what the fuck!!! 然后我就#vim /var/logs/message,发现了如下信息: 可见在00:46分的时候,我的prxdms被干掉了。再看看其他的机器,如图: 厉害了我的哥,直接把zabbix-agent都卡出来了,但是往上一翻,原来在zabbix-agent卡出来之前,predms已经自动跳出了。可见三台机器都是在00:47分的时候,内存暴涨,然后linux杀死了当前内存最大的程序。至于金山云的服务器为什么会在零点47分的时候有一次内存暴涨,那就不得而知了。 而这个情况就是oom-killer,也就是说linux系统会默认的给所有的程序分布一些内存供他们使用,但是这个分布的内存肯定是要大于他们正常的需要内存,这部分内存是属于每个进程的,内核直接回收利用的话比较麻烦,所以内核采用一种过度分配内存(over-commit memory)的办法来间接利用这部分 “空闲” 的内存,提高整体内存的使用效率。一般来说这样做没有问题,但当大多数应用程序都消耗完自己的内存的时候麻烦就来了,因为这些应用程序的内存需求加起来超出了物理内存(包括 swap)的容量,内核(OOM killer)必须杀掉一些进程才能腾出空间保障系统正常运行。 我们先看一下cat /proc/sys/vm/overcommit_memory 值0,可见目前采取的是启发策略,即Overcommit。 /proc/sys/vm/overcommit_memory 的值有3个,分别是0,1和2,具体含义如下: 0. 启发式策略。合理的overcommit会被接受,不合理的overcommit会被拒绝。1. 任何overcommit都会被接受。2. 当系统分配的内存超过swap+N%*物理RAM(N%由vm.overcommit_ratio决定)时,会拒绝commit。overcommit的策略通过vm.overcommit_memory设置。overcommit的百分比由vm.overcommit_ratio设置。 而云主机的配置本身就不会很高,而且像oracle、mysql、java这种程序又特别的吃内存,所以这两就是oom-killer的重灾户。 那么遇到这种情况怎么办?第一个方案掏钱升级内存大小,第二个方案就是更换体积更小的程序,或者是优化内存,如果前两个都不好使,那么就动点手脚,调整进程内存参数,不让他们过早的被oom发现,让oom先kill掉其他的进程。 这里主要说的是第三个方案,也就是动手脚。 每一个进程都有一个自己的进程号,即pid。linux是“一切皆文件”的系统,那么我们的pid文件就会出现在/proc/pid号码中。我们以一个zabbix_agent为例: 在/proc会对应每一个进程,有一个pid号码的文件夹,而这个文件夹里面又有很多文件,我们关注的就是这个oom_score的文件。这个数字是可以被我们手动通过oom_score_adj去调整的,而这个数字越小的话,进程被oom_kill的优先级越低,最小值是-1000,最大值是1000。 当然,如果对于脾气比较急的同学,可以直接把oom-killer这个项目干掉,干掉的方法如下: 1 2 #sysctl-wvm.overcommit_memory=2 #echo"vm.overcommit_memory=2">>/etc/sysctl.conf 但是,这个方法严重不推荐于生产环境... 还有,如果机器频繁出现oom-killer的话,那么就只能砸钱提升内存了,这一点是逃不掉的。反正花的也是老板的钱儿,你不用心疼。 [参考资料] http://lwn.net/Articles/317814/ https://linux-mm.org/OOM_Killer http://www.oracle.com/technetwork/articles/servers-storage-dev/oom-killer-1911807.html 本文转自 苏幕遮618 51CTO博客,原文链接:http://blog.51cto.com/chenx1242/1861667

优秀的个人博客,低调大师

Java与CPU缓存是如何亲密接触的!

在解释【伪共享】这个概念之前,我们先来运行一段代码,小编的电脑上有4个core。 这个程序的逻辑是4个线程共享同一个数组读写不同下标的变量。每个线程循环1亿次读写,也就是+1操作。然后统计4个线程同时跑完总共花的时间。 下面我们来看看在小编的电脑上运行的结果: 然后我把SharingLong里面的注释代码去掉,再跑了一下: 在性能上注释前后差别高达5比1,为什么会在性能上会产生如此大的差别呢? 这就是本篇要讲的主题【伪共享】,英文名叫False Sharing。而SharingLong里面的注释行一般称之为【缓存行填充】,英文名叫Cache Line Padding。 首先我们来计算一下SharingLong对象占用的内存空间,我们不考虑64位的情景,Java的对象都有一个2个word的头部,第一个word存储对象的hashcode和一些特殊的位标志,如GC的分代年龄、偏向锁标记等,第二个word存储对象的指针地址,一个word就是32位。然后加上v和6个p变量,总共就是8个long的长度,也就是64字节。 接下来我们要引入CPU缓存的概念。 现代的处理器一般都有3级缓存结构,L1、L2和L3,CPU直接访问主存是一个相对比较慢的操作,所以通过3级缓存来提升访存性能。我们将3个缓存当成一个整体来看待,它就是CPU缓存。缓存的制造成本非常昂贵,它一般要比主存空间小的多。 CPU在读主存的时候,会先将主存的一块数据加载到缓存上,然后在缓存上读取。当CPU写主存的时候,它会首先写缓存,在未来的某个时间点再一次性将缓存的数据全部刷回主存,这样就可以提高写操作的性能。因为计算机程序数据操作的局部性,CPU连续的指令倾向于访问相邻地址空间的数据,所以后续的读写操作有很大的概率可以直接在缓存上拿到数据。如果缓存上不存在,那就再去主存上加载进来。 缓存虽然小,但是也不是太小,CPU在加载主存数据时,如果一次性将整个Cache填满,但是接下来的指令访问的数据又不在缓存上,就会导致读浪费。另外如果只修改了其中几个字节的数据,但是得回写整个Cache到内存,这又会导致写浪费。 所以现代的CPU缓存一般是分行存储的,最小处理单位是一个行,这个行的长度一般来说就是上文提到的64字节,我们称之为【缓存行】。 SharingLong对象中v的值是volatile类型的,意味着CPU要保证v变量在不同线程之间的读写可见行。当CPU对v变量进行修改的时候会将数据立即回写至主存并将相应的缓存行置为失效。这样后续对v变量进行的读写操作都需要重新从内存中加载缓存行,这样就保证了其它线程读到的数据是最新的。 这点跟我们平常在Java基础教科书里提到的有点不一样。教科书里面为了便于新手理解,不会提及缓存,一般只会说volatile变量直接读写内存。 如果内存里有两个volatile变量在相邻的地址,两个cpu分别对v1和v2进行读和写操作,会发生什么情况呢?首先我们分解执行动作。图中的h表示对象头。 1、CPU1对v1进行读操作,将内存里的v1加载到缓存行里。 2、CPU2对v2进行读操作,将内存里的v2加载到缓存行里。 3、CPU1对v1进行写操作,将缓存里的v1修改,然后回写到主存再将缓存行置为失效。 4、CPU2对v2进行写操作,将缓存里的v2修改,然后回写到主存再将缓存行置为失效。 步骤1肯定先于步骤3,步骤2肯定先于步骤4。它们发生的顺序可能是 1->2->3->4 ,相当于两个CPU交叠运行,步骤1加载缓存行,步骤2发现数据就在缓存行里还是最新的,就省去了加载缓存行操作了,这时读操作做到了【共享】。紧接着步骤3正常进行写操作,然后步骤4来了,CPU2发现缓存行失效了,所以还得重新加载缓存行,然后再回写到主存再将缓存行置为失效。这里就发生了重复加载缓存行的现象,也即【写竞争】。如果不是volatile变量,步骤3的写操作是不会立即回写内存的,缓存行也就不会立即置为失效,这个时候步骤4来了CPU可以直接对缓存进行写操作,而不会出现浪费现象。我们称这种现象为【伪共享】,就是说这两个变量虽然共享同一个缓存行,但是它们之间会发生写竞争。 如果顺序是1->3->2->4,步骤1和步骤3的读操作这时就没能实现共享,还是会有浪费。 当系统的线程数越多时,写竞争越激烈,这种浪费就越多。 现在我们能明白为什么去掉注释后,程序会变慢,因为存在写竞争现象,数组中相邻的SharingLong.v共享了同一个缓存行。 那加上p1~p6这6个变量的意义是什么呢?我们看图。 我们发现加上6个long变量后,v1和v2将分别占用自己的缓存行,互不干扰,所以写竞争也就不存在了,效率自然就提升了。 不过缺点也是有的,就是缓存的利用率降低了,一个缓存行的空间才使用了1/4。这就是典型的空间换时间的场景。 例子中我们使用了volatile变量,那如果改成普通变量呢?我们运行一下,结果如下。 相当惊人,耗时上居然少了3个量级,这就是volatile在性能上的代价。普通变量不需要保证线程之间的读写的可见性,CPU对缓存修改后不需要立即回写内存,不存在写操作缓存穿透现象。而读操作也不需要总是重新从内存加载,那这个效率几乎完全就是缓存访问的效率,而对volatile变量的读写操作则接近内存访问的效率,差距自然如此明显。 你也许会问,知道这些有什么蛋用! 确是没什么蛋用,因为在现实世界,大部分操作都涉及到IO操作。根据水桶效应,其它环节优化到了极致,也无法提升整体的质量。 但是也不完全所有的应用都是IO操作型的,有一些场景下那是纯粹的内存操作。那么对于纯内存操作来说,理解【伪共享】知识可以帮你从性能上提升几倍甚至是几个数量级。 著名的disruptor框架正是使用了缓存行填充技术,才使得它的环形数组队列能如此高效。看wiki上的性能报告,disruptor的RingBuffer相比Java内置的ArrayBlockingQueue在OPS上高出近一个数量级,在队列延迟上则低了接近3个数量级。 原文发布时间为:2018-08-09本文作者:老钱本文来自云栖社区合作伙伴“Java后端技术”,了解相关信息可以关注“Java后端技术”

资源下载

更多资源
Mario

Mario

马里奥是站在游戏界顶峰的超人气多面角色。马里奥靠吃蘑菇成长,特征是大鼻子、头戴帽子、身穿背带裤,还留着胡子。与他的双胞胎兄弟路易基一起,长年担任任天堂的招牌角色。

Nacos

Nacos

Nacos /nɑ:kəʊs/ 是 Dynamic Naming and Configuration Service 的首字母简称,一个易于构建 AI Agent 应用的动态服务发现、配置管理和AI智能体管理平台。Nacos 致力于帮助您发现、配置和管理微服务及AI智能体应用。Nacos 提供了一组简单易用的特性集,帮助您快速实现动态服务发现、服务配置、服务元数据、流量管理。Nacos 帮助您更敏捷和容易地构建、交付和管理微服务平台。

Rocky Linux

Rocky Linux

Rocky Linux(中文名:洛基)是由Gregory Kurtzer于2020年12月发起的企业级Linux发行版,作为CentOS稳定版停止维护后与RHEL(Red Hat Enterprise Linux)完全兼容的开源替代方案,由社区拥有并管理,支持x86_64、aarch64等架构。其通过重新编译RHEL源代码提供长期稳定性,采用模块化包装和SELinux安全架构,默认包含GNOME桌面环境及XFS文件系统,支持十年生命周期更新。

Sublime Text

Sublime Text

Sublime Text具有漂亮的用户界面和强大的功能,例如代码缩略图,Python的插件,代码段等。还可自定义键绑定,菜单和工具栏。Sublime Text 的主要功能包括:拼写检查,书签,完整的 Python API , Goto 功能,即时项目切换,多选择,多窗口等等。Sublime Text 是一个跨平台的编辑器,同时支持Windows、Linux、Mac OS X等操作系统。

用户登录
用户注册