最新要闻
- 环球观焦点:Intel 56核心刚出生就落伍!AMD Zen4撕裂者下半年来袭:96核心
- 【新视野】力压美国印度!中国富豪全球第一:钟睒睒蝉联首富 马化腾张一鸣紧随其后
- 石榴汁弄衣服上怎么洗才能不会变干(石榴汁弄衣服上怎么洗)
- 环球最资讯丨机箱中的海景房 乔思伯TK-1双曲面侧透游戏机箱579元:颜值爆表
- 成都比亚迪、特斯拉、宝马三车相撞 特斯拉和宝马车轮飞了
- 【世界速看料】新能源汽车充电时为何要交停车费 专家:可防止充电之后不挪窝
- 当前热点-全球首枚3D打印火箭!美国“人族一号”发射失败
- 明年底有望普及!PCIe 5.0 SSD尴尬了 买的人太少:性能残血、价格死贵
- 我和你本应该各自好各自坏是什么歌?我和你本应该各自好各自坏歌词
- mirror男团中谁的人气最高?mirror男团年龄排序
- 亡羊补牢的亡是什么意思?亡羊补牢成语故事
- 班主任管理班级的策略与措施是什么?班主任教育随笔示范
- 《最终幻想16》新片段 宠物可以防止你迷路
- 卿卿日常李薇的真实身份是什么?卿卿日常郝葭死了吗?
- 质感旗舰!真我GT Neo5 SE未来感十足:纳米级光哑熔合工艺打造
- 女子不敢在隧道开车 交给无证男子驾驶 听到后果惊恐万分
手机
iphone11大小尺寸是多少?苹果iPhone11和iPhone13的区别是什么?
警方通报辅警执法直播中被撞飞:犯罪嫌疑人已投案
- iphone11大小尺寸是多少?苹果iPhone11和iPhone13的区别是什么?
- 警方通报辅警执法直播中被撞飞:犯罪嫌疑人已投案
- 男子被关545天申国赔:获赔18万多 驳回精神抚慰金
- 3天内26名本土感染者,辽宁确诊人数已超安徽
- 广西柳州一男子因纠纷杀害三人后自首
- 洱海坠机4名机组人员被批准为烈士 数千干部群众悼念
家电
环球最资讯丨WMS深入浅出
Android中Window的创建过程
在Android中,Window是与操作系统交互的最上层组件。当一个应用程序启动时,首先会创建一个Activity,并且将此活动附加到一个新的窗口上。
以下是Android中窗口的创建过程:
ActivityManagerService(AMS)接收到一个启动指令,AMS通知ActivityThread来处理请求。
(资料图片仅供参考)
ActivityThread启动一个名为"system_server"的进程,该进程负责系统级别的服务。
AMS
“启动”system_server
进程system_server
进程包含不同的系统服务,其中就包括ActivityManagerService (AMS)
,负责管理应用程序的生命周期以及任务栈等。当启动 Android 系统时,init
进程会执行init.rc
脚本,该脚本定义了在系统启动时需要启动的所有进程。其中包括zygote
进程和system_server
进程。而AMS
是由ActivityThread
启动并注册到system_server
的。具体过程如下:ActivityThread
中的main()
方法启动时,会创建一个ApplicationThread
对象,并调用ApplicationThread
的attach()
方法。- 在
ApplicationThread
的attach()
方法中,会创建SystemServerConnection
对象,并通过该对象连接到system_server
进程。 SystemServerConnection
对象通过Binder
机制注册到system_server
进程并获取IBinder
实例,这样system_server
进程就能够调用该对象提供的方法。- 此时
system_server
进程就可以使用ActivityManagerNative.getDefault()
获取AMS
所提供的服务,从而开始管理应用程序的生命周期。
所以,
system_server
进程不是直接拉起AMS
进程,而是先由ActivityThread
注册到system_server
进程,然后再由system_server
进程获取AMS
所提供的服务来进行应用程序管理工作。ApplicationThread是一个在应用程序进程内部的私有Binder线程,它允许其他进程通过Binder机制与应用程序交互,例如创建Activity、更新应用程序UI等。该线程通常由ActivityManagerService调用,在进程启动时创建,并在整个应用程序生命周期中存在。
在系统服务进程中,WindowManagerService (WMS)被启动。
WMS创建一个 WindowManager 对象,并与 Surface Flinger 进行通信,Surface Flinger 负责显示所有从应用程序发来的视图。
WMS调用DisplayManager Service,查找可用的显示设备和默认显示器的信息,以确定需要创建多少个物理窗口。每个物理窗口都对应一个SurfaceView对象,表示要在屏幕上呈现的视图内容。
ActivityThread开始加载所需的资源、类和代码库,并启动一个新的Activity。
在Activity的onCreate()方法中,调用setContentView(layout)方法,该方法将XML布局文件转换为视图树。ActivityManagerService将创建新的区域,创建一个新的窗口,并将其添加到Windows Manager Service中。
在Android中,视图树指的是屏幕上显示所有UI元素(View、ViewGroup)的结构。每个Activity都有自己的视图树,该树通常由一个叫做DecorView的根View开始。
更新机制:当发生界面更新时,不需要手动地去更新每个View或ViewGroup , 而是通过调用invalidate()或者postInvalidate()通知系统进行重绘更新整个视图树,会标记与其关联的视图(父、子视图)
dirty
,最后会在合适时间一起刷新掉。invalidate():这个方法会告诉系统当前控件状态已经过期,并请求重新绘制。但是它不能直接在子线程中使用,只能在主线程中使用。
postInvalidate() :和invalidate()一样,也是用来请求重绘界面, 不同之处就是,它可以在非ui线程中被调用,比如说asyncTask任务完成后重新记录ListView的高度等并且针对大多数情况是足够的。
在真正执行重绘前,系统会先把所有需要重绘的区域存起来放在一个列表中。接着遍历这个列表将所有需要更新的UI 绘制到Bitmap对象中,最后将Bitmap一次性复制到屏幕缓存里。
当Activity的窗口准备就绪后,WMS将发送一些事件给输入控制系统,例如:触摸屏动作、键盘按键等等,这样用户才能与刚创建的窗口进行交互。
总之,Window在Android中扮演着非常重要的角色, ViewGroup 和 View 对象以及跨应用程序的 Activity 之间的通信都依赖于它们。
WMS对view的管理
当 Activity 启动时,ActivityManagerService 会创建一个新的 Window,并使用 WindowManager 将其添加到窗口管理器的视图层次结构中。当需要显示新的 UI 组件时(例如对话框、Toast 等),应用程序会向 WindowManager 发出请求。WindowManager 将新的 View 或 ViewGroup 添加到与该应用程序相关联的 Window 上。
ViewRootImpl
ViewRootImpl 位于 Android Framework 层中,是 View 系统的总管,它是连接 Window Manager 和 View 系统的纽带。当 ActivityThread 启动应用程序后,便创建一个 PhoneWindow,而 PhoneWindow 内部拥有一个 ViewRootImpl 对象,实现Activity和Window和View树的构建、事件的分发、View的绘制和视图的更新等功能。
是 Android 系统中用来连接 Activity 的界面事件处理机制,其主要包括两个部分:
作为 WindowManagerGlobal 的内部类,用于在创建/每次动态更新界面时,控制构建窗口,并通过 WindowSession、SurfaceControl 和 View 将窗口信息和视图内容传递给 SurfaceFlinger 进行显示。
作为 View 类的内部类,用于承接所有涉及到的视图绘制或交互事件,并将这些事件反馈回应用程序。这个内部类能够捕获输入设备的第一部分 View 来自屏幕设备的输入事件,并根据需要从 ActivityManager 中获取最新的 UI 绘制。
当一个 Activity 被启动时,Android 系统在底层调用 PhoneWindow.setContentView() 函数并返回 DecorView 对象(ID 为-1),它是整个视图树的根节点。在中心控制循环之后,Android 系统会先将该视图树的布局测量传递到当前窗口(measure()),然后再发出重绘命令,在屏幕上绘制视图并填充组件。最后 draw() 方法被调用以展示所有的子视图和相应的父视图。在这整个过程中,ViewRootlmpl 充当了桥梁和协调员的角色,保证视图的快速渲染和正确地响应全部事件。
Choreographer
Choreographer 是一个系统级别的回调机制,主要作用是协调并掌控界面的刷新,确保动画和其他 UI 变化的流程的顺畅。当 UI 发生更新时,比如用户移动手指或者系统通知 View 需要重绘等,View 会向 Choreographer 注册一个回调 Choreographer.frameCallback(),结合 VSync(垂直同步,即图与图之间的时间间隔,在 Android 中默认为 16ms)来调整任务执行时间点。Choreographer 利用这个机制优化动画效果,确保界面刷新流畅。
Choreographer运行机制如下:
在UI线程中,Choreographer类会持有一份Vsync信号的引用。Vsync信号代表了显示器每秒的刷新次数。
Choreographer通过注册ViewRootImpl对象来监听输入事件。
当用户触发屏幕操作等事件时,input event被enqueue到主线程队列中。
Main Thread Looper每次从消息队列中读取message时,就会通知Choreographer发送处理。
每当Vsync信号到达,Choreographer收到回调后会计算当前应该绘制哪一帧画面,并标记所有需要更新的View及其所在的Window。
系统根据这些需要更新的Window & View 进行重绘。
重绘结束后,再次记录下需要更新的View或布局。
待下一个Vsync信号到达时,就会通知所有需要更新的View执行postInvalidate(相关方法)将对应的区域加入到重绘队列中准备重绘。
之后,计算渲染时机并更新Vsync信号时间戳,进入下一轮循环。
总之,Choreographer充当了一个类似合唱指挥的作用, 它能够确保Android UI的流畅性和稳定性。
Surface&Canvas
Surface和Canvas是Android中管理View绘制的重要对象。其中,Surface作为一个低层次的抽象,主要提供了基本的像素级的绘制操作,而Canvas则在其上提供了更高级别的图形绘制操作接口。
具体来说,在开发中,View通过获取自己的Canvas实例,使用drawXXX()方法对其进行绘制,即可形成视图元素的样式和布局等属性。然后,这样的操作会被SurfaceFlinger捕捉到并发送到Surface中,在底层完成实际的像素写入、缓存以及帧合成等操作,并将最终的效果呈现到设备上。
此外,Choreographer也有助于优化Surface和Canvas的协作,它可以监测系统的刷新频率和当前性能状况,根据这些信息调整各个应用和服务所需要的绘制和交互逻辑及时得到执行。
因此,三者之间的关系比较密切,一方面Canvas是View的绘制主体之一,为Surface中的操作提供了更加高层次的封装;另一方面,Surface则为Canvas提供了最终的显示和渲染环境;Choreographer则使得这样的协作可以在大部分情况下保持良好的稳定性和流畅程度。
SurfaceView的使用方法示例:
SurfaceView 是 Android 中专门用于在子线程中绘制 UI 的一个 View。
其实,SurfaceView是由 Surface、Canvas 和 SubThread 三部分组成:
- Surface:是UI线程和子线程之间的交互(内存共享队列等)。
- Canvas:负责绘图。
- SubThread:子线程。
在 SurfaceView 中,通过 Surface 来连接 UI 线程和子线程,将子线程中渲染后的图片展示到 UI 上。这样,在 UI 线程中就不需要再去处理绘制的工作了,只需要显示即可。
如下具体实例:
- XML布局
- Java代码
public class MyActivity extends Activity implements SurfaceHolder.Callback{ private SurfaceView surfaceView; private SurfaceHolder holder; private boolean running = false; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_my); surfaceView = (SurfaceView)findViewById(R.id.surface_view); holder = surfaceView.getHolder(); holder.addCallback(this); } @Override public void surfaceChanged(SurfaceHolder arg0, int arg1, int arg2, int arg3) { } @Override public void surfaceCreated(SurfaceHolder arg0) { running = true; new Thread(new Runnable() { public void run() { while (running) { Canvas canvas = null; try { // 获取Canvas对象 canvas = holder.lockCanvas(); if (canvas != null) { // 在Canvas上绘制具体内容 draw(canvas); } } finally { if (canvas != null) { // 解除Canvas锁定并提交修改 holder.unlockCanvasAndPost(canvas); } } // 线程休眠一段时间 try { Thread.sleep(10); } catch (InterruptedException e) { e.printStackTrace(); } } } }).start(); } @Override public void surfaceDestroyed(SurfaceHolder arg0) { running = false; } /** * 在Canvas上绘制具体内容的方法 */ private void draw(Canvas canvas) { // 具体绘制步骤省略... // 可以调用各种drawXXX方法实现绘制 }}
在什么情况下使用SurfaceView取决于你的需求。如果你需要在你的应用程序中绘制大量图形或动画,则使用SurfaceView通常更为适合。如果只是简单的静态图像,那么ImageView或其他视图控件就足够了。总之,相比其他视图控件而言,SurfaceView具有更好的性能和更多的灵活性。
Vsync
是一种基于垂直同步信号的时间同步机制。在Android中,设备GPU渲染界面的速率固定为每秒60帧,即16.67毫秒每帧。然而,CPU和GPU之间可能存在数据传输延迟或其他因素导致两者工作不协调。这就会导致画面撕裂、抖动或卡顿等现象。
为了解决这些问题,Android引入了VSync机制,以确保CPU和GPU的工作同步。具体实现方式是将VSync信号提供给应用程序,然后使应用程序在每个VSync前进行绘图,并在下一个VSync到来时显示该绘图。这样就可以确保CPU和GPU在同一个时间点上运行。
在Android系统中,VSync信号由硬件发出,它告诉设备硬件屏幕已经准备好接受新的缓冲区。然后,Choreographer将向应用程序发出VSync信号,以触发应用程序响应并执行相应的操作,如更新UI、执行动画等。
Dialog&Toast
dialog源码具体实现
Dialog类继承自Window类,通过内部包含的Window对象来实现对话框窗口的创建和管理。具体实现流程如下:
- 构造函数
Dialog有多个构造函数供选择,其中默认会调用样式为Theme_Dialog的构造函数。
- 创建并装载内容View
在Dialog中通过setContentView方法将指定的布局文件或View对象设为对话框的内容视图,并使用Window对象来实现该过程。
- 设置标题
可以使用setTitle方法设置对话框的标题,注意:要在创建内容前完成标题的设置才能让标题真正生效。
- 设置按钮及监听器
提供了设置多个普通按钮和列表对话框专用按钮的回调监听方法。
- 显示对话框
首先检查对话框已经拥有了一个Window对象,如果没有就创建一个默认的,并从ActivityManager中获取当前应用程序的WindowToken(Activiy控制焦点的Window)分配给这个Window对象,在最后通过show()方法显示出对话框。
此外,还需要关注触摸事件的处理,当对话框显示后,会开启会modalThread线程进行排他性操作,直到用户操作结束。
以上就是Dialog源码实现的基本流程。
使用dialog示例
使用Dialog可以显示各式各样的弹窗,例如提醒、确认等。以下是一些使用Dialog实例的方法:
根据Xml文件创建Dialog
- 新建一个Xml文件(例如:custom_dialog.xml),用来构建Dialog。
- 在Activity中,创建Dialog对象并通过指定Xml文件进行设置。
public class MainActivity extends Activity { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); Dialog dialog = new Dialog(this); dialog.setContentView(R.layout.custom_dialog); dialog.show(); // 返回按钮监听 Button button = dialog.findViewById(R.id.dialog_button); button.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { dialog.dismiss(); } }); }}
AlertDialog源码解析
===============
AlertDialog是Android的一个常用对话框组件,可以向用户显示一些提示信息并提供操作选项。
整体架构
继承关系
AlertDialog继承自Dialog类,而Dialog类又继承自Window类。Window类持有ViewRootImpl与DecorView对象,并为它们提供生命周期管理等功能。AlertDialog在此基础上实现了对话框的布局、样式和逻辑控制等功能。
public class AlertDialog extends Dialog implements DialogInterface { ...}
组成部分
AlertDialog大致可分为以下几个部分:
- 对话框标题
- 对话框内容区域
- 操作按钮
其中,对话框内容区域可能会包含普通文本、列表、自定义视图等多种类型的数据。
如何使用
显示一个AlertDialog
new AlertDialog.Builder(context) .setTitle(titleResId) .setMessage(messageResId) .setPositiveButton(R.string.ok, null) .show();
创建AlertDialog实例
AlertDialog内部有一个静态内部类Builder,用于创建AlertDialog实例。Builder通过设置各种属性来产生不同类型的AlertDialog,最后调用show()方法显示出来。
源码分析
我们下面看下AlertDialog.Builder中具体实现细节。
变量声明
private final P mParams;private int mTheme = 0;private boolean mCancelable = true;
Builder模式的核心之一就是将需要配置的参数封装到一个Builder类中,并提供链式调用API来设置各个参数的值。在AlertDialog.Builder中,变量mParams就是Builder所持有的参数集合。
构造函数
public Builder(@NonNull Context context) { this(context, resolveDialogTheme(context, 0));}public Builder(@NonNull Context context, @StyleRes int themeResId) { mContext = context; mTheme = themeResId; mCancelable = true; mInflater = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE); mButtonPositiveIconAttrId = R.attr.alertDialogButtonGroupStyle; mButtonNegativeIconAttrId = R.attr.alertDialogButtonGroupStyle; mButtonNeutralIconAttrId = R.attr.alertDialogButtonGroupStyle; mParams = createParameters();}
Builder的构造函数接收Context和themeResId两个参数。Context用于获取系统服务,比如LayoutInflater;而themeResId则用于设置AlertDialog的样式,如果没有指定,则使用默认样式。
createParameters()
protected P createParameters() { return (P) new AlertController.AlertParams(mContext, mTheme);}
createParameters()方法的作用是创建AlertController.AlertParams对象,并返回参数类型为P的对象。由于P是泛型,其实现类是AlertController.AlertParams(AlertDialog的内部类)。
setTitle()
public Builder setTitle(@StringRes int titleId) { mParams.mTitle = mParams.mContext.getText(titleId); return this;}public Builder setTitle(CharSequence title) { mParams.mTitle = title; return this;}
setTitle()方法用于设置AlertDialog的标题,可以接收String和StringRes两种类型的参数。
setMessage()
public Builder setMessage(@StringRes int messageId) { mParams.mMessage = mParams.mContext.getText(messageId); return this;}public Builder setMessage(CharSequence message) { mParams.mMessage = message; return this;}
setMessage()方法用于设置AlertDialog的消息文本。
setPositiveButton()
public Builder setPositiveButton(@StringRes int textId, final OnClickListener listener
使用AlertDialog
- 创建Builder,设置相应参数。
AlertDialog.Builder builder = new AlertDialog.Builder(this);builder.setTitle("Title");builder.setMessage("Message");builder.setPositiveButton("OK", new DialogInterface.OnClickListener() { public void onClick(DialogInterface dialog, int id) { // action for OK button } });builder.setNegativeButton("Cancel", new DialogInterface.OnClickListener() { public void onClick(DialogInterface dialog, int id) { // action for Cancel button } });
- 显示弹窗。
AlertDialog dialog = builder.create();dialog.show();
使用自定义Dialog
- 创建一个继承于Dialog的新类,重写构造方法,进行必要的初始化工作。
public class CustomDialog extends Dialog{ public CustomDialog(Context context) { super(context); setContentView(R.layout.custom_dialog); // setting properties } // setters of custom dialog components private String mValue; public void setValue(String value) { mValue = value; } // getters of custom dialog components public String getValue() { return mValue; }}
- 在需要的地方使用Dialog。
CustomDialog dialog_1 = new CustomDialog(this);button.setOnClickListener(new OnClickListener() { @Override public void onClick(View v) { CustomDialog dialog_1 = new CustomDialog(MainActivity.this); TextView display_value = dialog_1.findViewById(R.id.display_value); display_value.setText("Hello world!"); dialog_1.show(); } });
从WMS角度分析activity启动
从 WMS 的角度来分析 Activity 启动流程的具体过程:
- AMS 开始启动 Activity,调用 WMS 的 addWindow 方法,并传递一些参数。
- WMS 首先创建一个用于显示 Activity 的 View,并将其添加到 WindowManager 中。这个 View 通常是 PhoneWindow 类的实例。
- 接着,WMS 会根据 Activity 的属性设置窗口的类型和特性,例如是否全屏、有没有标题栏等。
- WMS 将 Activity 的 View 添加到 WindowManager 的视图树中,并计算出 Activity 窗口的大小和位置。
- 最后,WMS 通知 AMS 发送消息,即 Activity 已准备好并显示出来了。
Window的添加和删除过程如下:
Window的添加(也叫“拦截”)过程如下:
- ActivityManagerService(以下简称AMS)通过Binder机制向应用进程中的WMS发送启动Activity请求。
- WMS根据请求信息,创建新的WindowManager.LayoutParams。该LayoutParams中记录了窗口的各种参数,例如窗口类型、布局、大小、位置等等。
- WindowManagerGlobal类是一个单例类,WMS在创建完WindowManager.LayoutParams后,将该参数传入WindowManagerGlobal.addView()方法进行窗口的添加操作。注意,该方法并不会直接添加窗口View到DecorView中,而是创建两个辅助类ViewRootImpl和ViewRootImpl.Called。
- ViewRootImpl才是window真正的添加者,它在WindowManagerGlobal.addView()方法的内部实现中被调用。该类完成以下任务:
- 创建普通View或SurfaceView对象,并为之设置Context。
- 通过WindowManager.LayoutParams信息,初始化视图的测量和布局参数。“视图的测量大小”指的就是上文提到的 “sizeCompatMode”,即“全屏模式” 或 “裁剪屏幕模式”。这个模式的设置有一定的先后顺序。
- 注册Activity View监听器,在窗口状态发生变化时,通知Activity做出相应处理(如onResume()等)。
- 此时View已经准备好了,但我们需要通过WindowManager.addView()将测量和布局结果写入DecorView中。此措施足够友好地保障外部View和界面的稳定性和可靠性。
Window的移除过程如下:
- 当Activity销毁时,最顶层Window即DecorView要被移除。AMS接收到该 Activity 对象销毁的请求。
- AMS调用WMS的removeView时,wms判断getWindowListLocked()是否为空,如果不为空,那么调用对应的viewRootImpl.destroy()。
- 在destroy()方法中会调用 Surface.Release() 方法,把 surface 销毁掉。
- 接着,我们在 final i = mViews.indexOf(view) 将 mView 对应的 view 移除。
- 同时,我们还要将 ViewCallbacks,即 Activity 赋值 null,避免内存泄漏。
关键词:
-
环球关注:剑指 Offer 17. 打印从 1 到最大的 n 位数(java解题)
leetcode《图解数据结构》剑指Offer17 打印从1到最大的n位数(java解题)的解题思路和java代码,并附上...
来源: 天天简讯:权值(点分治)
当前速看:JavaScript学习笔记
环球最资讯丨WMS深入浅出
环球关注:剑指 Offer 17. 打印从 1 到最大的 n 位数(java解题)
环球观焦点:Intel 56核心刚出生就落伍!AMD Zen4撕裂者下半年来袭:96核心
【新视野】力压美国印度!中国富豪全球第一:钟睒睒蝉联首富 马化腾张一鸣紧随其后
石榴汁弄衣服上怎么洗才能不会变干(石榴汁弄衣服上怎么洗)
环球最资讯丨机箱中的海景房 乔思伯TK-1双曲面侧透游戏机箱579元:颜值爆表
成都比亚迪、特斯拉、宝马三车相撞 特斯拉和宝马车轮飞了
天天简讯:Go语言:利用 TDD 逐步为一个字典应用创建完整的 CRUD API
【世界播资讯】springcloud Stream整合rabbitmq消息驱动生产者踩坑
【天天报资讯】Vue之移动端viewport-vw适配
LevelDb-用户接口
世界视讯!Spring Cloud Alibaba微服务搭建(二)- 安装mysql
【世界速看料】新能源汽车充电时为何要交停车费 专家:可防止充电之后不挪窝
当前热点-全球首枚3D打印火箭!美国“人族一号”发射失败
明年底有望普及!PCIe 5.0 SSD尴尬了 买的人太少:性能残血、价格死贵
我和你本应该各自好各自坏是什么歌?我和你本应该各自好各自坏歌词
mirror男团中谁的人气最高?mirror男团年龄排序
亡羊补牢的亡是什么意思?亡羊补牢成语故事
班主任管理班级的策略与措施是什么?班主任教育随笔示范
《最终幻想16》新片段 宠物可以防止你迷路
看点:MS SQL服务器教程_编程入门自学教程_菜鸟教程-免费教程分享
卿卿日常李薇的真实身份是什么?卿卿日常郝葭死了吗?
质感旗舰!真我GT Neo5 SE未来感十足:纳米级光哑熔合工艺打造
女子不敢在隧道开车 交给无证男子驾驶 听到后果惊恐万分
196元暴涨至1910元 民宿回应五一价格翻十倍:先挂着 随时调整
最资讯丨专盯未成年?女孩添加“爱豆”QQ后被骗贷款3万4
连鸽两次 世界首枚3D打印火箭将再发射:这回能顺利吗?
全球热点!Python工具箱系列(二十八)
天天通讯!不知道
酝酿产智融合“化学反应” 浙江衢州集中签约多家研究院
天天日报丨“帝王座驾、以辇为尊” 比亚迪云辇系统官宣:或为底盘新技术
天天热文:早午餐合成一顿?医生提醒:细胞营养需求加大 更易长胖
即时看!警惕!义乌一女子险被电商“客服”骗走800万
当前观点:配可滑动中控屏、宾利同款B柱挂钩!极氪X内饰官图发布
每日看点!【数论与组合数学 3】Hensel 引理、原根
世界观察:Android使用SurfaceView实现签名板
每日聚焦:机器学习算法(三):基于horse-colic数据的KNN近邻(k-nearest neighbors)预测分类
全球微头条丨领域驱动设计DDD应用与最佳实践
环球观天下!Linux安装Redis教程
看热讯:小孩飞机票怎么收费
1000N连续旋转爆震 国内全新发动机点火成功:颠覆性优势
自爆卡车?奔驰EQE车库逆行:反怪特斯拉Model 3车主不让路
精选!男子在电竞酒店枕头下发现一窝老鼠 官方回应引网友吐槽:怎么能住
微头条丨8只海豚在美国海滩搁浅全部死亡 6只被安乐死
焦点速递!吉利全新SUV博越COOL官图发布:四出排气、1.5升发动机
要去海南旅游的老友们请注意,海南离岛免税购物,有新变化!
今日热闻!数据库系统原理之关系数据库
深入消息队列MQ,看这篇就够了!
全网最详细中英文ChatGPT-GPT-4示例文档-从0到1快速入门条目分类应用——官网推荐的48种最佳应用场景(附python/node.js/curl命令源
环球动态:以太网发明者鲍勃·梅特卡夫获图灵奖 计算机界的诺贝尔奖
又一股惨遭退市!市值暴跌99%
世界热议:《CS2》地图对比:起源2加持画质更明亮、细节丰富
去年净赚499亿元创纪录!保时捷2.7万名员工每人6.7万元奖金
Java八股文之基础篇
全球简讯:在 Arch Linux 中安装 GNOME 桌面所需步骤介绍
当你对 redis 说你中意的女孩是 Mia
环球时讯:琥珀手串会变色吗 琥珀手串会越戴越亮吗
环球看点!全球首个空中飞行出租车来了:巴黎开测 2024奥运会要用
【天天报资讯】抗早泄国产“伟哥”药物上市 市场有多大?专家称将翻倍增长 国内患者众多
全球首搭帝瓦雷音响!比亚迪腾势N7猎跑SUV亮相:运动低趴
当前速讯:鸡鸣寺游客爆满设反悔门引导离寺 网友神评:我佛果然慈悲 给反悔机会
全球今日报丨读C#代码整洁之道笔记04_重构C#代码识别代码坏味道
北方多地遭遇沙尘暴 PM爆表:气象台再发预警 还没退去
环球头条:流浪小狗乞求收养者一起带走玩具熊:画面让养狗人士泪目 为何被遗弃
今日关注:iPhone 14首发的车祸检测功能让人崩溃!苹果iOS 16.4将优化升级
世界热讯:读Java性能权威指南(第2版)笔记25_性能测试方法上
每日头条!LOL2023狗熊怎么出装(上单狗熊2023出装顺序)
精选!等了 11年 《CSGO2》电竞网游终于官宣:画质大升级 免费更新
天天简讯:使用C#开发微信公众号对接ChatGPT和DALL-E
今日关注:关于人工智能的思考,写在chatGPT爆火之时
Vue——initRender【八】
环球快讯:NVIDIA突然复活SLI!但不是你想的那样
每日看点!比尔·盖茨谈ChatGPT 赞其1980年以来最革命性技术进步
天天即时:爱子飞机上死亡:母亲怒告世界最大航司美国航空
谷歌的“GPT”终于憋出来了!但是 也不比百度强多少啊
当前热议!抖音救人一命!男子发头孢配酒视频获救:客服教科书式报警
头条:交700个税的工资多少_j700
今日讯!SEO优化:友情链接!真心换真心?
通过 poe 免费使用ChatGPT、GPT-4
天天观察:71.C++标准库类型string
CTAS建表时报错ORA-65114
Go HTTP编程
天天热点!苹果官方推荐!iNote灵感笔记新版发布:超紧凑模式来了
热讯:金士顿无敌了!拿下2022年全渠道SSD市场占有率第一
高德、口碑正式合并:阿里旗下本地到店业务将统一整合
热推荐:国科微:目前晶圆产能较前两年已趋于缓和
全球最新:关于基于AWS-Cli的方式对RDS资源批量添加tag的方法
全球微速讯:小红书去水印技巧合集(亲测有效!!!)
每日热点:Git基本使用
RHEL无法配置网关问题一则
世界快看点丨加快步伐!腾讯高管:“生成式AI”或纳入微信和QQ
天津金逸影城
2023年3月22日(软件工程日报)
阿里云大使和代理商的优惠的区别与选择
动态焦点:美债市场危机四伏 “安全资产”吸引力或进一步下降
3GB显存被封杀!《光环无限》都不让玩
Opera浏览器推送97.0.4719.26更新:集成ChatGPT与AI总结功能
世界速递!碧桂园打造湖湘人居典范 护航品质生活