简介

ActivityManagerService中对Activity的管理都是以Task的形式,任务Task是指在执行特定作业时与用户交互的一系列 Activity, 这些 Activity 按照各自的打开顺序排列在堆栈Stack中,AMS中分别以TaskRecord和ActivityStack表示,Activity则用ActivityRecord表示。因此我们也可以这么认为ActivityManagerService对Activity的管理,其实真正实现上来说是对ActivityStack,TaskRecord和ActivityRecord这三个数据结构的管理。更多详细的Task,Stack信息我们可以参考Google官网中Understand Tasks and Back Stack。
通常我们可以通过如下命令获取Android系统中Stack和Task的一些基本信息:

adb shell am stack list
Stack id=1 bounds=[0,0][240,320] displayId=0 userId=0taskId=142: com.android.settings/com.android.settings.Settings bounds=[0,0][240,320] userId=0 visible=true topActivity=ComponentInfo{com.android.settings/com.android.settings.Settings}Stack id=0 bounds=[0,0][240,320] displayId=0 userId=0taskId=139: com.android.launcher3/com.android.launcher3.Launcher bounds=[0,0][240,320] userId=0 visible=false topActivity=ComponentInfo{com.android.launcher3/com.android.launcher3.Launcher}

如果我们想要获取对应Stack中Task以及Task中Activity的详细信息,比如Task中Activity的数量,Activity的启动Intent,Activity的启动模式等等,我们可以通过如下命令:

ACTIVITY MANAGER ACTIVITIES (dumpsys activity activities)
Display #0 (activities from top to bottom):Stack #1:mFullscreen=trueisSleeping=falsemBounds=nullTask id #142mFullscreen=truemBounds=nullmMinWidth=-1mMinHeight=-1mLastNonFullscreenBounds=null* TaskRecord{32da96f #142 A=com.android.settings U=0 StackId=1 sz=1}userId=0 effectiveUid=1000 mCallingUid=u0a14 mUserSetupComplete=true mCallingPackage=com.android.launcher3affinity=com.android.settingsintent={act=android.intent.action.MAIN cat=[android.intent.category.LAUNCHER] flg=0x10200000 cmp=com.android.settings/.Settings}origActivity=com.android.settings/.SettingsrealActivity=com.android.settings/.SettingsautoRemoveRecents=false isPersistable=true numFullscreen=1 taskType=0 mTaskToReturnTo=1rootWasReset=true mNeverRelinquishIdentity=true mReuseTask=false mLockTaskAuth=LOCK_TASK_AUTH_PINNABLEActivities=[ActivityRecord{f46fe89 u0 com.android.settings/.Settings t142}]askedCompatMode=false inRecents=true isAvailable=truelastThumbnail=null lastThumbnailFile=/data/system_ce/0/recent_images/142_task_thumbnail.pngstackId=1hasBeenVisible=true mResizeMode=RESIZE_MODE_RESIZEABLE_VIA_SDK_VERSION mSupportsPictureInPicture=false isResizeable=true firstActiveTime=1672808557 lastActiveTime=1672809402 (inactive for 223s)* Hist #0: ActivityRecord{f46fe89 u0 com.android.settings/.Settings t142}packageName=com.android.settings processName=com.android.settingslaunchedFromUid=10014 launchedFromPackage=com.android.launcher3 userId=0app=ProcessRecord{218dd1e 2581:com.android.settings/1000}Intent { act=android.intent.action.MAIN cat=[android.intent.category.LAUNCHER] flg=0x10200000 cmp=com.android.settings/.Settings bnds=[159,155][237,242] }frontOfTask=true task=TaskRecord{32da96f #142 A=com.android.settings U=0 StackId=1 sz=1}taskAffinity=com.android.settingsrealActivity=com.android.settings/.SettingsbaseDir=/system/priv-app/Settings/Settings.apkdataDir=/data/user_de/0/com.android.settingsstateNotNeeded=false componentSpecified=true mActivityType=0compat={160dpi always-compat} labelRes=0x7f120b06 icon=0x7f0800df theme=0x7f1301c8mLastReportedConfigurations:mGlobalConfig={1.0 ?mcc?mnc [en_US] ldltr sw240dp w240dp h248dp 160dpi smll port -touch -keyb/v/h -nav/h appBounds=Rect(0, 0 - 240, 272) s.4}mOverrideConfig={1.0 ?mcc?mnc [en_US] ldltr sw240dp w240dp h248dp 160dpi smll port -touch -keyb/v/h -nav/h appBounds=Rect(0, 0 - 240, 272) s.4}CurrentConfiguration={1.0 ?mcc?mnc [en_US] ldltr sw240dp w240dp h248dp 160dpi smll port -touch -keyb/v/h -nav/h appBounds=Rect(0, 0 - 240, 272) s.4}taskDescription: iconFilename=/data/system_ce/0/recent_images/142_activity_icon_1672808529.png label="null" primaryColor=fff5f5f5backgroundColor=fffafafastatusBarColor=ff757575navigationBarColor=ff000000launchFailed=false launchCount=1 lastLaunchTime=-3m44s281mshaveState=false icicle=nullstate=RESUMED stopped=false delayedResume=false finishing=falsekeysPaused=false inHistory=true visible=true sleeping=false idle=true mStartingWindowState=STARTING_WINDOW_SHOWNfullscreen=true noDisplay=false immersive=false launchMode=2frozenBeforeDestroy=false forceNewConfig=falsemActivityType=APPLICATION_ACTIVITY_TYPEwaitingVisible=false nowVisible=true lastVisibleTime=-3m40s512msresizeMode=RESIZE_MODE_RESIZEABLE_VIA_SDK_VERSIONmLastReportedMultiWindowMode=false mLastReportedPictureInPictureMode=falseRunning activities (most recent first):TaskRecord{32da96f #142 A=com.android.settings U=0 StackId=1 sz=1}Run #0: ActivityRecord{f46fe89 u0 com.android.settings/.Settings t142}mResumedActivity: ActivityRecord{f46fe89 u0 com.android.settings/.Settings t142}Stack #0:mFullscreen=trueisSleeping=falsemBounds=nullTask id #139mFullscreen=truemBounds=nullmMinWidth=-1mMinHeight=-1mLastNonFullscreenBounds=null* TaskRecord{b1b0e06 #139 I=com.android.launcher3/.Launcher U=0 StackId=0 sz=1}userId=0 effectiveUid=u0a14 mCallingUid=1000 mUserSetupComplete=true mCallingPackage=nullintent={act=android.intent.action.MAIN cat=[android.intent.category.HOME] flg=0x10000100 cmp=com.android.launcher3/.Launcher}realActivity=com.android.launcher3/.LauncherautoRemoveRecents=false isPersistable=true numFullscreen=1 taskType=1 mTaskToReturnTo=0rootWasReset=false mNeverRelinquishIdentity=true mReuseTask=false mLockTaskAuth=LOCK_TASK_AUTH_PINNABLEActivities=[ActivityRecord{1f09444 u0 com.android.launcher3/.Launcher t139}]askedCompatMode=false inRecents=true isAvailable=truelastThumbnail=null lastThumbnailFile=/data/system_ce/0/recent_images/139_task_thumbnail.pngstackId=0hasBeenVisible=true mResizeMode=RESIZE_MODE_RESIZEABLE mSupportsPictureInPicture=false isResizeable=true firstActiveTime=1667109722 lastActiveTime=1672808679 (inactive for 224s)* Hist #0: ActivityRecord{1f09444 u0 com.android.launcher3/.Launcher t139}packageName=com.android.launcher3 processName=com.android.launcher3launchedFromUid=0 launchedFromPackage=null userId=0app=ProcessRecord{31ae0ef 3012:com.android.launcher3/u0a14}Intent { act=android.intent.action.MAIN cat=[android.intent.category.HOME] flg=0x10000100 cmp=com.android.launcher3/.Launcher }frontOfTask=true task=TaskRecord{b1b0e06 #139 I=com.android.launcher3/.Launcher U=0 StackId=0 sz=1}taskAffinity=nullrealActivity=com.android.launcher3/.LauncherbaseDir=/system/priv-app/Launcher3Go/Launcher3Go.apkdataDir=/data/user/0/com.android.launcher3stateNotNeeded=true componentSpecified=false mActivityType=1compat={160dpi always-compat} labelRes=0x7f0c000d icon=0x7f020021 theme=0x7f120002mLastReportedConfigurations:mGlobalConfig={1.0 ?mcc?mnc [en_US] ldltr sw240dp w240dp h248dp 160dpi smll port -touch -keyb/v/h -nav/h appBounds=Rect(0, 0 - 240, 272) s.4}mOverrideConfig={1.0 ?mcc?mnc [en_US] ldltr sw240dp w240dp h248dp 160dpi smll port -touch -keyb/v/h -nav/h appBounds=Rect(0, 0 - 240, 272) s.4}CurrentConfiguration={1.0 ?mcc?mnc [en_US] ldltr sw240dp w240dp h248dp 160dpi smll port -touch -keyb/v/h -nav/h appBounds=Rect(0, 0 - 240, 272) s.4}taskDescription: iconFilename=null label="null" primaryColor=fff5f5f5backgroundColor=fffafafastatusBarColor=0navigationBarColor=0launchFailed=false launchCount=0 lastLaunchTime=-1h38m41s610mshaveState=true icicle=Bundle[mParcelledData.dataSize=4096]state=STOPPED stopped=true delayedResume=false finishing=falsekeysPaused=false inHistory=true visible=false sleeping=false idle=true mStartingWindowState=STARTING_WINDOW_NOT_SHOWNfullscreen=true noDisplay=false immersive=false launchMode=2frozenBeforeDestroy=false forceNewConfig=falsemActivityType=HOME_ACTIVITY_TYPEwaitingVisible=false nowVisible=false lastVisibleTime=-43m15s482msresizeMode=RESIZE_MODE_RESIZEABLEmLastReportedMultiWindowMode=false mLastReportedPictureInPictureMode=falseRunning activities (most recent first):TaskRecord{b1b0e06 #139 I=com.android.launcher3/.Launcher U=0 StackId=0 sz=1}Run #0: ActivityRecord{1f09444 u0 com.android.launcher3/.Launcher t139}mLastPausedActivity: ActivityRecord{1f09444 u0 com.android.launcher3/.Launcher t139}
Display #1 (activities from top to bottom):ResumedActivity: ActivityRecord{f46fe89 u0 com.android.settings/.Settings t142}mFocusedStack=ActivityStack{4f3c6a8 stackId=1, 1 tasks} mLastFocusedStack=ActivityStack{4f3c6a8 stackId=1, 1 tasks}mCurTaskIdForUser={0=142}mUserStackInFront={}mStacks={0=ActivityStack{7020d13 stackId=0, 1 tasks}, 1=ActivityStack{4f3c6a8 stackId=1, 1 tasks}}mLockTaskModeState=NONE  mLockTaskPackages (userId:packages)=0:[]mLockTaskModeTasks[]KeyguardController:mKeyguardShowing=falsemKeyguardGoingAway=falsemOccluded=falsemDismissingKeyguardActivity=nullmDismissalRequested=falsemVisibilityTransactionDepth=0

至于为什么使用如上命令就能获取这么多的信息,建议还是去多多的阅读系统源码,或许我们可以找到我们想要的答案。

ActivityManagerService中的Stack

Android系统中一些常用的Stack

Name Value Description
HOME_STACK_ID 0 一般HomeActivity所在的Stack,就是Launcher所在的Stack
FULLSCREEN_WORKSPACE_STACK_ID 1 正常情况下,我们启动的Activity都在这个Stack
FREEFORM_WORKSPACE_STACK_ID 2 自由模式下,一般平板中会使用
DOCKED_STACK_ID 3 进入分屏模式后,新创建的便是该类型的Stack
PINNED_STACK_ID 4 画中画模式下,处于画中画Activity所在的Stack
RECENTS_STACK_ID 5 SystemUI的RecentActivity所在的Stack
ASSISTANT_STACK_ID 6 有Android assistant启动的Activity都在此Stack,国内手机貌似很少使用该Stack

从这些常用的Stack的作用上来看,我们可以简单的理解Android更多的会根据各种不同的行为和场景来区分不同的ActivityStack。从之前的dump信息我们便可以断定ActivityStack中主要存放的就是各种Task,对应的便是TaskRecord,实际Android代码中也确实如此。对于ActivityStack的各种管理,Android又抽象出ActivityStackSupervisor类,我们从命名中也可以看出该类专门负责ActivityStack的管理。后续Activity的启动流程分析中,我们将更多的接触并分析该类。一般Android系统启动时,开机启动到Launcher界面,便会创建HOME_STACK_ID Stack(下面便是开机的Trace Log,可以结合Trace和代码具体理一下这个创建的过程,这里就不再细述了)专门用于存放Home Activity。

01-20 23:40:35.110  1964  1964 D ABM_TRACE_MAIN: java.lang.Throwable
01-20 23:40:35.110  1964  1964 D ABM_TRACE_MAIN:    at com.android.server.am.ActivityStack.<init>(ActivityStack.java:458)
01-20 23:40:35.110  1964  1964 D ABM_TRACE_MAIN:    at com.android.server.am.ActivityStackSupervisor.createStack(ActivityStackSupervisor.java:2657)
01-20 23:40:35.110  1964  1964 D ABM_TRACE_MAIN:    at com.android.server.am.ActivityStackSupervisor.createStackOnDisplay(ActivityStackSupervisor.java:2648)
01-20 23:40:35.110  1964  1964 D ABM_TRACE_MAIN:    at com.android.server.am.ActivityStackSupervisor.getStack(ActivityStackSupervisor.java:2251)
01-20 23:40:35.110  1964  1964 D ABM_TRACE_MAIN:    at com.android.server.am.ActivityStackSupervisor.setWindowManager(ActivityStackSupervisor.java:689)
01-20 23:40:35.110  1964  1964 D ABM_TRACE_MAIN:    at com.android.server.am.ActivityManagerService.setWindowManager(ActivityManagerService.java:2629)
01-20 23:40:35.110  1964  1964 D ABM_TRACE_MAIN:    at com.android.server.SystemServer.startOtherServices(SystemServer.java:861)
01-20 23:40:35.110  1964  1964 D ABM_TRACE_MAIN:    at com.android.server.SystemServer.run(SystemServer.java:398)
01-20 23:40:35.110  1964  1964 D ABM_TRACE_MAIN:    at com.android.server.SystemServer.main(SystemServer.java:274)
01-20 23:40:35.110  1964  1964 D ABM_TRACE_MAIN:    at java.lang.reflect.Method.invoke(Native Method)
01-20 23:40:35.110  1964  1964 D ABM_TRACE_MAIN:    at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:438)
01-20 23:40:35.110  1964  1964 D ABM_TRACE_MAIN:    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:787)
01-20 23:40:35.129  1964  1964 I wm_stack_created: 0
01-20 23:40:35.140  1964  1964 D ABM_TRACE_MAIN: java.lang.Throwable
01-20 23:40:35.140  1964  1964 D ABM_TRACE_MAIN:    at com.android.server.am.ActivityStackSupervisor$ActivityDisplay.attachStack(ActivityStackSupervisor.java:4749)
01-20 23:40:35.140  1964  1964 D ABM_TRACE_MAIN:    at com.android.server.am.ActivityStack.postAddToDisplay(ActivityStack.java:514)
01-20 23:40:35.140  1964  1964 D ABM_TRACE_MAIN:    at com.android.server.am.ActivityStack.<init>(ActivityStack.java:472)
01-20 23:40:35.140  1964  1964 D ABM_TRACE_MAIN:    at com.android.server.am.ActivityStackSupervisor.createStack(ActivityStackSupervisor.java:2657)
01-20 23:40:35.140  1964  1964 D ABM_TRACE_MAIN:    at com.android.server.am.ActivityStackSupervisor.createStackOnDisplay(ActivityStackSupervisor.java:2648)
01-20 23:40:35.140  1964  1964 D ABM_TRACE_MAIN:    at com.android.server.am.ActivityStackSupervisor.getStack(ActivityStackSupervisor.java:2251)
01-20 23:40:35.140  1964  1964 D ABM_TRACE_MAIN:    at com.android.server.am.ActivityStackSupervisor.setWindowManager(ActivityStackSupervisor.java:689)
01-20 23:40:35.140  1964  1964 D ABM_TRACE_MAIN:    at com.android.server.am.ActivityManagerService.setWindowManager(ActivityManagerService.java:2629)
01-20 23:40:35.140  1964  1964 D ABM_TRACE_MAIN:    at com.android.server.SystemServer.startOtherServices(SystemServer.java:861)
01-20 23:40:35.140  1964  1964 D ABM_TRACE_MAIN:    at com.android.server.SystemServer.run(SystemServer.java:398)
01-20 23:40:35.140  1964  1964 D ABM_TRACE_MAIN:    at com.android.server.SystemServer.main(SystemServer.java:274)
01-20 23:40:35.140  1964  1964 D ABM_TRACE_MAIN:    at java.lang.reflect.Method.invoke(Native Method)
01-20 23:40:35.140  1964  1964 D ABM_TRACE_MAIN:    at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:438)
01-20 23:40:35.140  1964  1964 D ABM_TRACE_MAIN:    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:787)
01-20 23:40:35.141  1964  1964 V ABM_Log : attachStack: attaching ActivityStack{abbc88a stackId=0, 0 tasks} to displayId=0 position=0

一般我们可以通过event log可以获取ActivityStack的创建与销毁

wm_stack_created (StackId|1|5)
wm_task_removed (TaskId|1|5),(Reason|3)

虽然这是WindowManagerService相关的Log,但是Window在组织和管理各种窗口时ActivityManagerService管理Activity一样都是通过各种堆栈形式的,并且WindowManagerService里面对应的堆栈顺序都是和ActivityManagerService中保持一致的,他们在Activity启动时创建的顺序也是一前一后的,其中相关的数据结构的对应关系如下:

ActivityStack    TaskStack
TaskRecord  Task
ActivityRecord  APPWindowToken

一般我们在创建Activity时,根据不同功能的需要,创建对应或使用不同的ActivityStack,一般使用ActivityStackSupervisor.getStack去获取,如果不存在便创建新的。对应的当我们Activity销毁的时候,Android系统会从该Activity所在的Task中移除该Activity,如果该Activity是lastActivity,系统还会从ActivityStack中移除该Task,如果从ActivityStack移除完该Task之后,ActivityStack中不存在任何Task,系统还会将该ActivityStack销毁回收。

ActivityManagerService中的Task

Activity启动过程中,对于ActivityStack应用开发者很少接触, 我们也可以不去关注它的创建与销毁,更多的这都是系统完成的。通过前文ActivityManagerService解读之Activity启动再探所述,我们知道可以更多的使用不同的启动模式,外加各种Task属性和设置不同的Intent flag来影响Activity Task的创建管理行为。比如每次需要Activity创建单独的Task时您可以使用singleInstance模式,等等(更多关于启动模式和Task属性以及不同intent flag请参阅ActivityManagerService解读之Activity启动再探一文)。当我们启动Activity或者销毁Activity时,系统为该Activity创建Task或者销毁Task时候,我们一般会看见如下Log:

wm_task_created (TaskId|1|5),(StackId|1|5)
am_create_task (User|1|5),(Task ID|1|5)wm_task_removed (TaskId|1|5),(Reason|3)

Task是从用户角度来管理Activity的,Android系统更多的是根据用户的操作来将一系列Activity按启动顺序放于同一个Task中,这些Activity可以来自不同的应用,因为从用户角度来说,这些操作只是为自己服务而已,用户并不知道他们来自不同的应用。

写在最后

ActivityStack和TaskRecord是ActivityManagerService管理Activity的两个相当重要的数据,了解他们的作用对分析Activity启动大有作用,懂得Activity启动流程,在日常项目开发中才能应对各种需求,实施各种不同的应对方案,比如最近很火的插件技术,想要插件话Activity,必须得了解Activity的启动流程,又比如优化应用的启动速度等等。

ActivityManagerService解读之Activity启动三探--Activity中Task与Stack相关推荐

  1. 【Android 插件化】Hook 插件化框架 ( 从 Hook 应用角度分析 Activity 启动流程 一 | Activity 进程相关源码 )

    Android 插件化系列文章目录 [Android 插件化]插件化简介 ( 组件化与插件化 ) [Android 插件化]插件化原理 ( JVM 内存数据 | 类加载流程 ) [Android 插件 ...

  2. 深入理解Activity启动流程(二)–Activity启动相关类的类图

    本文原创作者:Cloud Chou. 欢迎转载,请注明出处和本文链接 本系列博客将详细阐述Activity的启动流程,这些博客基于Cm 10.1源码研究. 在介绍Activity的详细启动流程之前,先 ...

  3. 重拾Activity(三)Activity知识

    这篇文章是从安卓开发者文档找到的Activity资料进行整理的(篇幅较长,用于个人回顾) 目录 这篇文章是从安卓开发者文档找到的Activity资料进行整理的(篇幅较长,用于个人回顾) Activit ...

  4. Activity启动另一个Activity并返回的完整生命周期

    Android的简单基本问题,这里记录一下 从一个Activity创建后启动另一个Activity并返回的完整log输出: 从log可以看出,当前Activity启动另一个Activity时,总是要等 ...

  5. Activity(三)—— Activity的启动模式

    Activity的启动模式 1 Activity的LaunchMode Activity为什么需要启动模式?在默认情况下,当我们多次启动同一个Activity的时候,系统会创建多个实例并把它们一一放入 ...

  6. Activity启动另一个Activity的方式总结

    下面两种方式均采用这个menifests.xml布局,且下面两种方式属于显性方式{即通过使用(MainActivity.this, xxxx.class)}: 一,用intent构造器进行启动: 二, ...

  7. ActivityManagerService解读之Activity启动时间闲聊--Android Framework层时间计算介绍

    从ActivityManagerService解读之Activity启动初探,到ActivityManagerService解读之Activity启动再探,到ActivityManagerServic ...

  8. ActivityManagerService解读之Activity启动初探

    Activity是Android四大组建之一,负责用户交互界面展示,其重要性不可言喻.Android系统由ActivityManagerService负责管理Activity.熟悉Activity的启 ...

  9. 深入理解Activity启动流程(三)–Activity启动的详细流程2

    本文原创作者:Cloud Chou. 欢迎转载,请注明出处和本文链接 本系列博客将详细阐述Activity的启动流程,这些博客基于Cm 10.1源码研究. 深入理解Activity启动流程(一)--A ...

  10. Activity启动过程源码流程梳理和解读

    篇章目标要点 AMS(全称ActivityManagerService)作为四大组件的管理者,在Android系统工作流程当中起着非常重要的角色,四大组件当中Activity使用则又最为广泛,因为了解 ...

最新文章

  1. 剑指offer面试题6:重建二叉树
  2. vsftpd服务安装与虚拟用户配置
  3. [CentOS7] systemd
  4. Android 6.0 7.0 8.0 一个简单的app内更新版本-okgo app版本更新
  5. C语言基础:C语言宏定义(4) - 多文件编译
  6. Postgresql的HashJoin状态机流程图整理
  7. docker容器内没有yum命令_为什么不建议把数据库部署在Docker容器内?
  8. css优雅降级和渐进增强
  9. ajax同步异步问题
  10. MATLAB每个字母等宽,等宽文本文件的导入选项对象
  11. SpringBoot根据包名进行区分使用多数据源
  12. 图解机器学习算法(9) | GBDT模型详解(机器学习通关指南·完结)
  13. 电信跨域跨系统业务实践
  14. Openwrt:创建编译IPK软件包
  15. Centos文件夹目录中文变英文
  16. python画五环图_对Python安装及绘制五环图的初步认识,初识,pythonpython,与
  17. npm ERR! fatal: unable to access ‘https://github.com/adobe-webplatform/eve.git/‘: OpenSSL SSL_read:
  18. 量子纠缠的机制是什么?一定要理解整体性概念
  19. 客制化键盘编程_基于3D打印的客制化机械键盘设计与实现
  20. npm run build appeared(出现) Cannot find module ‘webpack/lib/ModuleFilenameHelpers‘

热门文章

  1. 亚马逊防关联方法适合shopee平台吗?
  2. VSCode远程控制服务器
  3. matlab心理学函数包,心理学研究方法:基于MATLAB和PSYCHTOOLBOX
  4. 主流编程语言的特点以及优缺点(一)
  5. springboot项目启动后执行方法
  6. ros系列—解决文件改名导致节点无法启动问题及ros::NodeHandle nh与nh(“~“)的理解
  7. 连接共享打印机时,弹出无法安装打印机,打印处理器不存在!!
  8. 《#华为云#听从你心,无问西东》及网友跟帖
  9. oracle detele,Oracle中,一个Delete操作的流程
  10. 访黏度计算公式_调节阀流量系数Kv的计算公式