硬件渲染器初始化从 ViewRootImpl 类 setView(…) 方法中调用 enableHardwareAcceleration(…) 开始。

HardwareRenderer 是一个抽象类,代表使用硬件加速渲染视图层次结构的接口。

首先找到 mHardwareRenderer 赋值的位置,我们才能确认它具体是什么子类。这在 ViewRootImpl 类 setView 方法中调用 enableHardwareAcceleration(…) 方法启用硬件加速开始。

frameworks/base/core/java/android/view/ViewRootImpl.java

public final class ViewRootImpl implements ViewParent,View.AttachInfo.Callbacks, HardwareRenderer.HardwareDrawCallbacks {......public void setView(View view, WindowManager.LayoutParams attrs, View panelParentView) {synchronized (this) {if (mView == null) {mView = view;......// 如果应用程序拥有 Surface,不要启用硬件加速if (mSurfaceHolder == null) {enableHardwareAcceleration(attrs);}  ......}......}......}......
}
  1. 创建硬件渲染器类实例
  2. 给硬件渲染器设置名称

frameworks/base/core/java/android/view/ViewRootImpl.java

public final class ViewRootImpl implements ViewParent,View.AttachInfo.Callbacks, HardwareRenderer.HardwareDrawCallbacks {......private void enableHardwareAcceleration(WindowManager.LayoutParams attrs) {mAttachInfo.mHardwareAccelerated = false;mAttachInfo.mHardwareAccelerationRequested = false;// 当应用程序处于兼容模式时,不要启用硬件加速if (mTranslator != null) return;// 如果需要,尝试启用硬件加速final boolean hardwareAccelerated =(attrs.flags & WindowManager.LayoutParams.FLAG_HARDWARE_ACCELERATED) != 0;if (hardwareAccelerated) {if (!HardwareRenderer.isAvailable()) {return;}// 持久性进程(包括系统)不应在低端设备上进行加速渲染。// 在这种情况下,将设置 sRendererDisabled。 // 此外,系统进程本身绝不应进行加速渲染。 // 在这种情况下,将同时设置 sRendererDisabled 和 sSystemRendererDisabled。// 设置 sSystemRendererDisabled 时,// 系统进程中的代码可以使用 PRIVATE_FLAG_FORCE_HARDWARE_ACCELERATED 启用硬件加速绘图。//(这基本上是用于锁定屏幕的)final boolean fakeHwAccelerated = (attrs.privateFlags &WindowManager.LayoutParams.PRIVATE_FLAG_FAKE_HARDWARE_ACCELERATED) != 0;final boolean forceHwAccelerated = (attrs.privateFlags &WindowManager.LayoutParams.PRIVATE_FLAG_FORCE_HARDWARE_ACCELERATED) != 0;if (fakeHwAccelerated) {// 这仅用于窗口管理器显示的用于启动应用程序的预览窗口,// 因此它们看起来更像是正在启动的应用程序。mAttachInfo.mHardwareAccelerationRequested = true;} else if (!HardwareRenderer.sRendererDisabled|| (HardwareRenderer.sSystemRendererDisabled && forceHwAccelerated)) {if (mAttachInfo.mHardwareRenderer != null) {mAttachInfo.mHardwareRenderer.destroy();}final Rect insets = attrs.surfaceInsets;final boolean hasSurfaceInsets = insets.left != 0 || insets.right != 0|| insets.top != 0 || insets.bottom != 0;final boolean translucent = attrs.format != PixelFormat.OPAQUE || hasSurfaceInsets;// 1. 创建硬件渲染器类实例mAttachInfo.mHardwareRenderer = HardwareRenderer.create(mContext, translucent);if (mAttachInfo.mHardwareRenderer != null) {// 2. 给硬件渲染器设置名称mAttachInfo.mHardwareRenderer.setName(attrs.getTitle().toString());mAttachInfo.mHardwareAccelerated =mAttachInfo.mHardwareAccelerationRequested = true;}}}}......
}

使用 OpenGL 创建一个硬件渲染器。HardwareRenderer 实际为 ThreadedRenderer 类。

frameworks/base/core/java/android/view/HardwareRenderer.java

public abstract class HardwareRenderer {....../*** @param translucent True 如果 Surface 是半透明的为 true,否则为 false* @return 一个由OpenGL支持的硬件渲染器。*/static HardwareRenderer create(Context context, boolean translucent) {HardwareRenderer renderer = null;if (DisplayListCanvas.isAvailable()) {renderer = new ThreadedRenderer(context, translucent);}return renderer;}......
}

硬件渲染器,它将渲染代理给渲染线程。大多数调用目前是同步的。UI 线程可以在渲染线程上阻塞,但是渲染线程绝对不能在 UI 线程上阻塞。ThreadedRenderer 创建一个 RenderProxy 实例。RenderProxy 反过来在 RenderThread 上创建和管理 CanvasContext。 CanvasContext 由 RenderProxy 的生命周期完全管理。

请注意,虽然目前 EGL 上下文和 Surface 是由渲染线程创建和管理的,但目标是将其移动到一个共享结构中,可以由两个线程管理。EGLSurface 的创建和删除应该在 UI 线程上完成,而不是在渲染线程上完成,以避免 Surface 缓冲区分配造成渲染线程的阻塞。

ThreadedRenderer 构造函数主要完成了以下工作:

  1. 获取由主题指定的光影属性
  2. 调用 nCreateRootRenderNode 创建 RenderNode
  3. 调用 nCreateProxy 创建 RenderProxy

frameworks/base/core/java/android/view/ThreadedRenderer.java

public class ThreadedRenderer extends HardwareRenderer {......// 由主题指定的光影属性private final float mLightY;private final float mLightZ;private final float mLightRadius;private final int mAmbientShadowAlpha;private final int mSpotShadowAlpha;......private long mNativeProxy;......private RenderNode mRootNode;......ThreadedRenderer(Context context, boolean translucent) {final TypedArray a = context.obtainStyledAttributes(null, R.styleable.Lighting, 0, 0);mLightY = a.getDimension(R.styleable.Lighting_lightY, 0);mLightZ = a.getDimension(R.styleable.Lighting_lightZ, 0);mLightRadius = a.getDimension(R.styleable.Lighting_lightRadius, 0);mAmbientShadowAlpha =(int) (255 * a.getFloat(R.styleable.Lighting_ambientShadowAlpha, 0) + 0.5f);mSpotShadowAlpha = (int) (255 * a.getFloat(R.styleable.Lighting_spotShadowAlpha, 0) + 0.5f);a.recycle();long rootNodePtr = nCreateRootRenderNode();// 采用现有的本地渲染节点。mRootNode = RenderNode.adopt(rootNodePtr);// 设置渲染节点是否应该将自身剪切到其边界。该属性由视图的父视图控制。mRootNode.setClipToBounds(false);mNativeProxy = nCreateProxy(translucent, rootNodePtr);ProcessInitializer.sInstance.init(context, mNativeProxy);loadSystemProperties();}    ......
}

nCreateRootRenderNode 是一个 jni 方法,Native 对应实现为 android_view_ThreadedRenderer_createRootRenderNode(…) 方法。

frameworks/base/core/java/android/view/ThreadedRenderer.java

public class ThreadedRenderer extends HardwareRenderer {......private static native long nCreateRootRenderNode();     ......
}

new 出来 Native RootRenderNode 对象,然后设置名称为 “RootRenderNode”,最后将 RootRenderNode 对象指针强转为 jlong 返回到 Java 层。

frameworks/base/core/jni/android_view_ThreadedRenderer.cpp

namespace android {
......
static jlong android_view_ThreadedRenderer_createRootRenderNode(JNIEnv* env, jobject clazz) {RootRenderNode* node = new RootRenderNode(env);node->incStrong(0);node->setName("RootRenderNode");return reinterpret_cast<jlong>(node);
}
......
const char* const kClassPathName = "android/view/ThreadedRenderer";static JNINativeMethod gMethods[] = {......{ "nCreateRootRenderNode", "()J", (void*) android_view_ThreadedRenderer_createRootRenderNode },......
};int register_android_view_ThreadedRenderer(JNIEnv* env) {return RegisterMethodsOrDie(env, kClassPathName, gMethods, NELEM(gMethods));
}};

渲染节点是个什么?用于存储已记录的画布命令以及每个 View/ViewGroup 显示属性。画布命令的记录与 SkPicture 有点类似,除了画布记录功能在 DisplayListCanvas(用于管理记录),DisplayListData(用于保存实际数据)和 DisplayList(用于保存属性并在渲染器上执行回放)之间划分。请注意,当刷新视图记录的画布操作流时,DisplayListData 从单个 DisplayList 的下面换出。DisplayList(及其属性)保持 attach 状态。

再来分析 nCreateProxy(…) 方法。它是一个 jni 函数,对应 Native 实现为 android_view_ThreadedRenderer_createProxy(…) 方法。

frameworks/base/core/java/android/view/ThreadedRenderer.java

public class ThreadedRenderer extends HardwareRenderer {......private static native long nCreateProxy(boolean translucent, long rootRenderNode); ......
}
  1. 将 rootRenderNodePtr jlong 强转回 RootRenderNode* 指针
  2. 创建 ContextFactoryImpl 对象,其内部持有 RootRenderNode
  3. 创建 RenderProxy 渲染代理对象

frameworks/base/core/jni/android_view_ThreadedRenderer.cpp

namespace android {
......
static jlong android_view_ThreadedRenderer_createProxy(JNIEnv* env, jobject clazz,jboolean translucent, jlong rootRenderNodePtr) {RootRenderNode* rootRenderNode = reinterpret_cast<RootRenderNode*>(rootRenderNodePtr);ContextFactoryImpl factory(rootRenderNode);return (jlong) new RenderProxy(translucent, rootRenderNode, &factory);
}
......
const char* const kClassPathName = "android/view/ThreadedRenderer";static JNINativeMethod gMethods[] = {......{ "nCreateProxy", "(ZJ)J", (void*) android_view_ThreadedRenderer_createProxy },......
};int register_android_view_ThreadedRenderer(JNIEnv* env) {return RegisterMethodsOrDie(env, kClassPathName, gMethods, NELEM(gMethods));
}};

RenderProxy 是严格的单线程化。所有方法都必须在所属线程上调用。

  1. 调用 RenderThread 类 getInstance() 获取 RenderThread 渲染线程单例,赋值给 RenderProxy 成员变量 mRenderThread
  2. 展开 SETUP_TASK 宏定义,得到指向 createContextArgs 结构体的指针 args,createContextArgs 结构体是在编译期间 CREATE_BRIDGE4 宏定义展开后定义的,其中还实现了函数 Bridge_createContext,return 语句就是其函数体。这个函数在展开 SETUP_TASK 宏定义时作为入参传入 MethodInvokeRenderTask 构造函数
  3. 给 createContextArgs 结构体成员 translucent、rootRenderNode、thread 和 contextFactory 赋值
  4. mContext 是指向 CanvasContext* 的指针成员,调用 postAndWait(…) 函数传入实参 MethodInvokeRenderTask 对象,返回值赋给 mContext,实际就是指向 CREATE_BRIDGE4 宏最后 new 出来的 CanvasContext 对象。此函数将渲染任务添加到了渲染线程
  5. mDrawFrameTask 是一个 DrawFrameTask 成员,代表绘制帧任务,调用其 setContext(…) 方法设置上下文,入参为 RenderThread 和 CanvasContext*。

frameworks/base/libs/hwui/renderthread/RenderProxy.cpp

namespace android {
namespace uirenderer {
namespace renderthread {
......
#define ARGS(method) method ## Args
......
#define CREATE_BRIDGE4(name, a1, a2, a3, a4) CREATE_BRIDGE(name, a1,a2,a3,a4,,,,)
......
#define CREATE_BRIDGE(name, a1, a2, a3, a4, a5, a6, a7, a8) \typedef struct { \a1; a2; a3; a4; a5; a6; a7; a8; \} ARGS(name); \static void* Bridge_ ## name(ARGS(name)* args)#define SETUP_TASK(method) \LOG_ALWAYS_FATAL_IF( METHOD_INVOKE_PAYLOAD_SIZE < sizeof(ARGS(method)), \"METHOD_INVOKE_PAYLOAD_SIZE %zu is smaller than sizeof(" #method "Args) %zu", \METHOD_INVOKE_PAYLOAD_SIZE, sizeof(ARGS(method))); \MethodInvokeRenderTask* task = new MethodInvokeRenderTask((RunnableMethod) Bridge_ ## method); \ARGS(method) *args = (ARGS(method) *) task->payload()
......   
CREATE_BRIDGE4(createContext, RenderThread* thread, bool translucent,RenderNode* rootRenderNode, IContextFactory* contextFactory) {return new CanvasContext(*args->thread, args->translucent,args->rootRenderNode, args->contextFactory);
}
......
RenderProxy::RenderProxy(bool translucent, RenderNode* rootRenderNode, IContextFactory* contextFactory): mRenderThread(RenderThread::getInstance()), mContext(nullptr) {SETUP_TASK(createContext);args->translucent = translucent;args->rootRenderNode = rootRenderNode;args->thread = &mRenderThread;args->contextFactory = contextFactory;mContext = (CanvasContext*) postAndWait(task);mDrawFrameTask.setContext(&mRenderThread, mContext);
}
......
} /* namespace renderthread */
} /* namespace uirenderer */
} /* namespace android */

调用 RenderThread 类 getInstance() 方法可获得单例 RenderThread 对象。getInstance() 方法定义在 Singleton.h 中,Singleton 类是一个模板单例类,getInstance() 方法会返回对应的 TYPE* 指针。RenderThread 类继承自 Singleton 因此就可以返回 RenderThread* 指针。

system/core/include/utils/Singleton.h

template <typename TYPE>
class ANDROID_API Singleton
{
public:static TYPE& getInstance() {Mutex::Autolock _l(sLock);TYPE* instance = sInstance;if (instance == 0) {instance = new TYPE();sInstance = instance;}return *instance;}static bool hasInstance() {Mutex::Autolock _l(sLock);return sInstance != 0;}protected:~Singleton() { };Singleton() { };private:Singleton(const Singleton&);Singleton& operator = (const Singleton&);static Mutex sLock;static TYPE* sInstance;
};

getInstance() 会调用 RenderThread 类无参构造函数。

  1. 初始化了一系列成员变量
  2. mFrameCallbackTask 赋值为 DispatchFrameCallbacks 对象
  3. mLooper 赋值为 Looper 对象
  4. 启动 RenderThread 线程

frameworks/base/libs/hwui/renderthread/RenderThread.cpp

RenderThread::RenderThread() : Thread(true), Singleton<RenderThread>(), mNextWakeup(LLONG_MAX), mDisplayEventReceiver(nullptr), mVsyncRequested(false), mFrameCallbackTaskPending(false), mFrameCallbackTask(nullptr), mRenderState(nullptr), mEglManager(nullptr) {Properties::load();mFrameCallbackTask = new DispatchFrameCallbacks(this);mLooper = new Looper(false);run("RenderThread");
}

启动线程之后,重点需要关注 threadLoop() 函数返回值。

Thread 对象有两种使用方法:

loop:如果 threadLoop() 返回 true,则在 requestExit() 未被调用时再次调用。
once:如果 threadLoop() 返回 false,则该线程将在返回时退出。

这里配置为 false,代表只运行一次,但 threadLoop() 函数体内部存在一个“无限” for 循环,结合 Looper 一起使用。这里处理了所有 RenderTask(渲染任务)。

frameworks/base/libs/hwui/renderthread/RenderThread.cpp

bool RenderThread::threadLoop() {setpriority(PRIO_PROCESS, 0, PRIORITY_DISPLAY);initThreadLocals();int timeoutMillis = -1;for (;;) {int result = mLooper->pollOnce(timeoutMillis);LOG_ALWAYS_FATAL_IF(result == Looper::POLL_ERROR,"RenderThread Looper POLL_ERROR!");nsecs_t nextWakeup;// 如果我们有任务的话,处理我们的队列while (RenderTask* task = nextTask(&nextWakeup)) {// 调用 task run() 方法task->run();// 任务本身可能已经删除,不要再引用它}if (nextWakeup == LLONG_MAX) {timeoutMillis = -1;} else {// 计算下一次唤醒时间nsecs_t timeoutNanos = nextWakeup - systemTime(SYSTEM_TIME_MONOTONIC);timeoutMillis = nanoseconds_to_milliseconds(timeoutNanos);if (timeoutMillis < 0) {timeoutMillis = 0;}}// 处理帧回调注册if (mPendingRegistrationFrameCallbacks.size() && !mFrameCallbackTaskPending) {drainDisplayEventQueue();mFrameCallbacks.insert(mPendingRegistrationFrameCallbacks.begin(), mPendingRegistrationFrameCallbacks.end());mPendingRegistrationFrameCallbacks.clear();// 请求 vsync 信号requestVsync();}if (!mFrameCallbackTaskPending && !mVsyncRequested && mFrameCallbacks.size()) {// TODO: Clean this up. This is working around an issue where a combination// of bad timing and slow drawing can result in dropping a stale vsync// on the floor (correct!) but fails to schedule to listen for the// next vsync (oops), so none of the callbacks are run.// 请求 vsync 信号requestVsync();}}return false;
}

最后总结一下它们的类图关系。

在这里插入图片描述

查看全文
如若内容造成侵权/违法违规/事实不符,请联系编程学习网邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!

相关文章

  1. 电脑入门的学习方法和技巧

    我们都知道当今社会是一个高速发展信息时代。在各行各业中都离不开信息的处理,这正是计算机被广泛应用于信息管理系统的环境原因。使用计算机进行信息处理,不仅提高了工作效率,而且大大提高了其安全性。作为21世纪的人才,如果你对外说你不懂电脑的话,那就显得你特别的低人…...

    2024/5/1 13:44:28
  2. act_hi_varinst 流程引擎重复数据提交问题处理

    在多服务并发提交数据时,可导致流程数据重复,造成审批数据困扰。为避免重复数据提交,可创建数据库组合唯一性约束 创建数据库约束 --创建约束 ALTER TABLE "public"."act_hi_varinst" ADD CONSTRAINT "CK_act_hi_varinst_001" UNIQUE ("…...

    2024/4/16 1:06:27
  3. python实现有道翻译

    初学爬虫,利用urllib模块实现有道翻译 import urllib.request import urllib.parse import jsondef main():content = input(请输入要翻译的内容:)# 翻译地址request_url = http://fanyi.youdao.com/translate?smartresult=dict&smartresult=rule# data参数data = {i: c…...

    2024/5/1 9:46:43
  4. 分治,排列的逆序数

    思路: 根据归并算法改编,分治 总体大概是,分成两半,左边的逆序数+右边的逆序数+左边的一个数和右边一个数组成的逆序对的数量 关键在于如何求左边的一个数,和右边一个数组成的逆序对的数量 可以吧左右两边排序从大到小,然后两个指针,i和j开始分别指向左边第一个和右边第一个.然…...

    2024/5/1 7:39:19
  5. python元类的简单了解

    一、什么是元类? 在python中一切皆对象,那么类是否也是对象呢?通过class关键字产生的类的实例,我们已经很熟悉了,但是通过class关键字产生的类的类就是元类。 class Bar:passb1 = Bar() print(type(b1)) #<class __main__.Bar>print(type(Bar)) #<class type>…...

    2024/4/19 16:55:48
  6. git 版本从本地提交代码到服务器上

    git从本地提交代码到服务器:1、将要提交的代码放到指定的文件夹下,进入要提交代码的项目文件夹中。2、设置用户名和邮箱:git config --global user.name 用户名 //用户名的字符串要用 " " 包含起来git config --global user.email 邮箱名 //邮箱名…...

    2024/5/1 7:47:41
  7. MySQL学习总结--DCL

    * SQL分类:1. DDL:操作数据库和表2. DML:增删改表中数据3. DQL:查询表中数据4. DCL:管理用户,授权* DBA:数据库管理员* DCL:管理用户,授权1. 管理用户1. 添加用户:* 语法:CREATE USER 用户名@主机名 IDENTIFIED BY 密码;2. 删除用户:* 语法:DROP USER 用户名@主机…...

    2024/4/16 1:06:17
  8. jdk源码解析(初识)

    jdk源码解析(初识) 源码解析的过程 是经历 JDK —>JRE—>JVM三部重要的步骤Java各种集成开发工具:类似我们在用的IDEA,MyEclipse等开发工具。 JDK:是面向开发人员使用的SDK,它提供了Java的开发环境和运行环境,简称软件开发包。 JRE:JRE运行环境是一个软件,它可…...

    2024/5/1 7:45:03
  9. 在html中链接怎么返回上一页面

    代码如下bai 超链接返回上一页代码: <a href=”bai#” onClick=”javascript :history.back(-1);”>返回上一页du</a><a href=”#” onClick=”javascript :history.go(-1);”>返回上一页</a>用按钮代码: <input type=”button” name=”Submit”…...

    2024/5/1 5:34:36
  10. java如何替换word中${}中的内容?

    转载自品略图书馆 http://www.pinlue.com/article/2019/11/0108/129757686840.html处理Word可以使用poi,如何替换使用下面三个类就好了。public class GenericTokenParser { private final String openToken; private final String closeToken; private final TokenHandler ha…...

    2024/5/1 5:08:16
  11. 搭建ActiveMQ服务

    1、apt-get安装 更新软件包 apt-get update sudo apt upgrade 安装jdk sudo apt install default-jdk 安装、启动 ActiveMQ sudo apt install activemq sudo systemctl start activemq 查看 sudo systemctl status activemq netstat -nl|grep 61616 netstat -nl|grep 8161 解决…...

    2024/5/1 5:56:00
  12. GitHub 星标 17K,超火的SpringBoot +Vue实战项目,贼全文档视频

    项目摘要vhr 是一个基于 SpringBoot+Vue 技术栈开发的前后端分离项目,项目使用 SpringBoot2.1.8 来开发,集成了当前企业级开发中众多的热门技术点,如消息中间件、Redis 缓存、SpringBoot+Vue+ElementUI 技术栈等等。技术选型核心框架:SpringBoot2.1.8安全管理:Spring Secu…...

    2024/5/1 7:51:00
  13. 面试官:简单的聊一下Zookeeper的ZAB协议?结果能回答正确的没几个

    前言Zab(Zookeeper Atomic Broadcast)是为ZooKeeper协设计的崩溃恢复原子广播协议,它保证zookeeper集群数据的一致性和命令的全局有序性。概念介绍在介绍zab协议之前首先要知道zookeeper相关的几个概念,才能更好的了解zab协议。集群角色 Leader:同一时间集群总只允许有一个…...

    2024/5/1 6:07:56
  14. 电脑键盘按键都代表着什么意思?

    F1F12通常称为功能键,其中F指的是Function功能的意思,说明F1F12是12个功能键。每一个电脑键盘标配都是顶端都有F1~F12一排按键。我估计全部掌握的人还真不算多,今天高手君就给大家普及一下F1~F12键在日常Windows系统中的功能和使用。注意,仅限台式机或者笔记本的外接键盘。…...

    2024/5/1 13:21:32
  15. laravel 数据验证规则

    return [accepted => 必须为yes,on,1,true,active_url => 是否是一个合法的url,基于PHP的checkdnsrr函数,因此也可以用来验证邮箱地址是否存在,after:date => 验证字段必须是给定日期后的值,比如required|date|after:tomorrow,通过PHP函数strtotime来验证,after_or_…...

    2024/5/1 10:05:09
  16. linux clone() 函数 实例

    百度clone实例,全特么是同一个文章的内容,都是讲的clone这个函数的用法,实际的例子一个都没找到,只好翻出以前不知道哪里修修补补的一个例子,复制到博客,留着以后忘了再来复习 /**clone进程的函数体 */ int clone_print(int argv) { printf(“clone fun argv is %d clone…...

    2024/4/16 1:06:17
  17. 页面加载后就执行一个js函数

    <script type="text/javascript"> function myfun() { alert("this window.onload"); }方法一: <body onload="myfunction()">方法二: <script type="text/javascript"> function myfun() { alert("this win…...

    2024/4/16 1:06:52
  18. javascript从入门到跑路-----js学习笔记(3)------循环结构

    **javascript从入门到跑路-----js学习笔记目录**循环结构:四个固定的内容:==>1.初始值==>2.条件判断==>3.要执行的代码==>4.自身的改变一.while循环==>while,中文 当...时,其实就是当满足条件时就执行代码,一旦不满足了就不执行==>语法:while(条件){满足条…...

    2024/4/16 1:06:27
  19. Hexo个人博客搭建教程

    有图片版本教程请看https://www.fanis.cloud/2020/07/11/Hexo%E4%B8%AA%E4%BA%BA%E5%8D%9A%E5%AE%A2%E6%90%AD%E5%BB%BA%E6%95%99%E7%A8%8B/ Hexo个人博客搭建教程 1 搭建前准备 1.1 环境配置 需要安装git、node,最后安装hexo 1.1.1 安装Git: 首先看电脑是否已经安装了git gi…...

    2024/4/16 1:05:31
  20. Java基础之Collections框架Map接口及其源码分析

    Java基础之Collections框架Map接口及其源码分析Map简单使用迭代的使用Java8 使用Map接口源码分析 将键映射到值的对象。 映射不能包含重复的键; 每个键最多可以映射到一个值. 该接口代替了Dictionary类,后者是一个完全抽象的类,而不是一个接口。 Map接口包括用于基本操作(例…...

    2024/4/18 22:47:12

最新文章

  1. Q1营收稳健增长,云从科技如何在“百模大战”的险中求稳?

    自从迈入大模型时代&#xff0c;AI行业可谓“一天一个样”。越来越多的企业涌现&#xff0c;舆论热议从未断绝。 但就像所有技术必须经历的那些考验&#xff0c;在现实尺度下&#xff0c;AI顺利走进商业化世界&#xff0c;仍然是少部分玩家掌握的稀缺能力。个中原因不尽相同&a…...

    2024/5/1 13:58:08
  2. 梯度消失和梯度爆炸的一些处理方法

    在这里是记录一下梯度消失或梯度爆炸的一些处理技巧。全当学习总结了如有错误还请留言&#xff0c;在此感激不尽。 权重和梯度的更新公式如下&#xff1a; w w − η ⋅ ∇ w w w - \eta \cdot \nabla w ww−η⋅∇w 个人通俗的理解梯度消失就是网络模型在反向求导的时候出…...

    2024/3/20 10:50:27
  3. Mac brew 安装软件

    Mac brew 安装软件 homebrew 速度慢 将brew 切换到国内镜像源 # 速度一般 # 步骤一 cd "$(brew --repo)" git remote set-url origin https://mirrors.tuna.tsinghua.edu.cn/git/homebrew/brew.git# 步骤二 cd "$(brew --repo)/Library/Taps/homebrew/homebr…...

    2024/4/30 3:19:50
  4. 论文阅读AI工具链

    文献检索 可以利用智谱清言来生成合适的文献检索式&#xff0c;并根据需要不断调整。 谷歌学术 在Google Scholar中进行检索时&#xff0c;您可以使用类似的逻辑来构建您的搜索式&#xff0c;但是语法会有所不同。Google Scholar的搜索框接受普通的文本搜索&#xff0c;但是…...

    2024/5/1 13:38:40
  5. 【外汇早评】美通胀数据走低,美元调整

    原标题:【外汇早评】美通胀数据走低,美元调整昨日美国方面公布了新一期的核心PCE物价指数数据,同比增长1.6%,低于前值和预期值的1.7%,距离美联储的通胀目标2%继续走低,通胀压力较低,且此前美国一季度GDP初值中的消费部分下滑明显,因此市场对美联储后续更可能降息的政策…...

    2024/4/29 23:16:47
  6. 【原油贵金属周评】原油多头拥挤,价格调整

    原标题:【原油贵金属周评】原油多头拥挤,价格调整本周国际劳动节,我们喜迎四天假期,但是整个金融市场确实流动性充沛,大事频发,各个商品波动剧烈。美国方面,在本周四凌晨公布5月份的利率决议和新闻发布会,维持联邦基金利率在2.25%-2.50%不变,符合市场预期。同时美联储…...

    2024/4/30 18:14:14
  7. 【外汇周评】靓丽非农不及疲软通胀影响

    原标题:【外汇周评】靓丽非农不及疲软通胀影响在刚结束的周五,美国方面公布了新一期的非农就业数据,大幅好于前值和预期,新增就业重新回到20万以上。具体数据: 美国4月非农就业人口变动 26.3万人,预期 19万人,前值 19.6万人。 美国4月失业率 3.6%,预期 3.8%,前值 3…...

    2024/4/29 2:29:43
  8. 【原油贵金属早评】库存继续增加,油价收跌

    原标题:【原油贵金属早评】库存继续增加,油价收跌周三清晨公布美国当周API原油库存数据,上周原油库存增加281万桶至4.692亿桶,增幅超过预期的74.4万桶。且有消息人士称,沙特阿美据悉将于6月向亚洲炼油厂额外出售更多原油,印度炼油商预计将每日获得至多20万桶的额外原油供…...

    2024/4/30 18:21:48
  9. 【外汇早评】日本央行会议纪要不改日元强势

    原标题:【外汇早评】日本央行会议纪要不改日元强势近两日日元大幅走强与近期市场风险情绪上升,避险资金回流日元有关,也与前一段时间的美日贸易谈判给日本缓冲期,日本方面对汇率问题也避免继续贬值有关。虽然今日早间日本央行公布的利率会议纪要仍然是支持宽松政策,但这符…...

    2024/4/27 17:58:04
  10. 【原油贵金属早评】欧佩克稳定市场,填补伊朗问题的影响

    原标题:【原油贵金属早评】欧佩克稳定市场,填补伊朗问题的影响近日伊朗局势升温,导致市场担忧影响原油供给,油价试图反弹。此时OPEC表态稳定市场。据消息人士透露,沙特6月石油出口料将低于700万桶/日,沙特已经收到石油消费国提出的6月份扩大出口的“适度要求”,沙特将满…...

    2024/4/27 14:22:49
  11. 【外汇早评】美欲与伊朗重谈协议

    原标题:【外汇早评】美欲与伊朗重谈协议美国对伊朗的制裁遭到伊朗的抗议,昨日伊朗方面提出将部分退出伊核协议。而此行为又遭到欧洲方面对伊朗的谴责和警告,伊朗外长昨日回应称,欧洲国家履行它们的义务,伊核协议就能保证存续。据传闻伊朗的导弹已经对准了以色列和美国的航…...

    2024/4/28 1:28:33
  12. 【原油贵金属早评】波动率飙升,市场情绪动荡

    原标题:【原油贵金属早评】波动率飙升,市场情绪动荡因中美贸易谈判不安情绪影响,金融市场各资产品种出现明显的波动。随着美国与中方开启第十一轮谈判之际,美国按照既定计划向中国2000亿商品征收25%的关税,市场情绪有所平复,已经开始接受这一事实。虽然波动率-恐慌指数VI…...

    2024/4/30 9:43:09
  13. 【原油贵金属周评】伊朗局势升温,黄金多头跃跃欲试

    原标题:【原油贵金属周评】伊朗局势升温,黄金多头跃跃欲试美国和伊朗的局势继续升温,市场风险情绪上升,避险黄金有向上突破阻力的迹象。原油方面稍显平稳,近期美国和OPEC加大供给及市场需求回落的影响,伊朗局势并未推升油价走强。近期中美贸易谈判摩擦再度升级,美国对中…...

    2024/4/27 17:59:30
  14. 【原油贵金属早评】市场情绪继续恶化,黄金上破

    原标题:【原油贵金属早评】市场情绪继续恶化,黄金上破周初中国针对于美国加征关税的进行的反制措施引发市场情绪的大幅波动,人民币汇率出现大幅的贬值动能,金融市场受到非常明显的冲击。尤其是波动率起来之后,对于股市的表现尤其不安。隔夜美国股市出现明显的下行走势,这…...

    2024/4/25 18:39:16
  15. 【外汇早评】美伊僵持,风险情绪继续升温

    原标题:【外汇早评】美伊僵持,风险情绪继续升温昨日沙特两艘油轮再次发生爆炸事件,导致波斯湾局势进一步恶化,市场担忧美伊可能会出现摩擦生火,避险品种获得支撑,黄金和日元大幅走强。美指受中美贸易问题影响而在低位震荡。继5月12日,四艘商船在阿联酋领海附近的阿曼湾、…...

    2024/4/28 1:34:08
  16. 【原油贵金属早评】贸易冲突导致需求低迷,油价弱势

    原标题:【原油贵金属早评】贸易冲突导致需求低迷,油价弱势近日虽然伊朗局势升温,中东地区几起油船被袭击事件影响,但油价并未走高,而是出于调整结构中。由于市场预期局势失控的可能性较低,而中美贸易问题导致的全球经济衰退风险更大,需求会持续低迷,因此油价调整压力较…...

    2024/4/26 19:03:37
  17. 氧生福地 玩美北湖(上)——为时光守候两千年

    原标题:氧生福地 玩美北湖(上)——为时光守候两千年一次说走就走的旅行,只有一张高铁票的距离~ 所以,湖南郴州,我来了~ 从广州南站出发,一个半小时就到达郴州西站了。在动车上,同时改票的南风兄和我居然被分到了一个车厢,所以一路非常愉快地聊了过来。 挺好,最起…...

    2024/4/29 20:46:55
  18. 氧生福地 玩美北湖(中)——永春梯田里的美与鲜

    原标题:氧生福地 玩美北湖(中)——永春梯田里的美与鲜一觉醒来,因为大家太爱“美”照,在柳毅山庄去寻找龙女而错过了早餐时间。近十点,向导坏坏还是带着饥肠辘辘的我们去吃郴州最富有盛名的“鱼头粉”。说这是“十二分推荐”,到郴州必吃的美食之一。 哇塞!那个味美香甜…...

    2024/4/30 22:21:04
  19. 氧生福地 玩美北湖(下)——奔跑吧骚年!

    原标题:氧生福地 玩美北湖(下)——奔跑吧骚年!让我们红尘做伴 活得潇潇洒洒 策马奔腾共享人世繁华 对酒当歌唱出心中喜悦 轰轰烈烈把握青春年华 让我们红尘做伴 活得潇潇洒洒 策马奔腾共享人世繁华 对酒当歌唱出心中喜悦 轰轰烈烈把握青春年华 啊……啊……啊 两…...

    2024/5/1 4:32:01
  20. 扒开伪装医用面膜,翻六倍价格宰客,小姐姐注意了!

    原标题:扒开伪装医用面膜,翻六倍价格宰客,小姐姐注意了!扒开伪装医用面膜,翻六倍价格宰客!当行业里的某一品项火爆了,就会有很多商家蹭热度,装逼忽悠,最近火爆朋友圈的医用面膜,被沾上了污点,到底怎么回事呢? “比普通面膜安全、效果好!痘痘、痘印、敏感肌都能用…...

    2024/4/27 23:24:42
  21. 「发现」铁皮石斛仙草之神奇功效用于医用面膜

    原标题:「发现」铁皮石斛仙草之神奇功效用于医用面膜丽彦妆铁皮石斛医用面膜|石斛多糖无菌修护补水贴19大优势: 1、铁皮石斛:自唐宋以来,一直被列为皇室贡品,铁皮石斛生于海拔1600米的悬崖峭壁之上,繁殖力差,产量极低,所以古代仅供皇室、贵族享用 2、铁皮石斛自古民间…...

    2024/4/28 5:48:52
  22. 丽彦妆\医用面膜\冷敷贴轻奢医学护肤引导者

    原标题:丽彦妆\医用面膜\冷敷贴轻奢医学护肤引导者【公司简介】 广州华彬企业隶属香港华彬集团有限公司,专注美业21年,其旗下品牌: 「圣茵美」私密荷尔蒙抗衰,产后修复 「圣仪轩」私密荷尔蒙抗衰,产后修复 「花茵莳」私密荷尔蒙抗衰,产后修复 「丽彦妆」专注医学护…...

    2024/4/30 9:42:22
  23. 广州械字号面膜生产厂家OEM/ODM4项须知!

    原标题:广州械字号面膜生产厂家OEM/ODM4项须知!广州械字号面膜生产厂家OEM/ODM流程及注意事项解读: 械字号医用面膜,其实在我国并没有严格的定义,通常我们说的医美面膜指的应该是一种「医用敷料」,也就是说,医用面膜其实算作「医疗器械」的一种,又称「医用冷敷贴」。 …...

    2024/4/30 9:43:22
  24. 械字号医用眼膜缓解用眼过度到底有无作用?

    原标题:械字号医用眼膜缓解用眼过度到底有无作用?医用眼膜/械字号眼膜/医用冷敷眼贴 凝胶层为亲水高分子材料,含70%以上的水分。体表皮肤温度传导到本产品的凝胶层,热量被凝胶内水分子吸收,通过水分的蒸发带走大量的热量,可迅速地降低体表皮肤局部温度,减轻局部皮肤的灼…...

    2024/4/30 9:42:49
  25. 配置失败还原请勿关闭计算机,电脑开机屏幕上面显示,配置失败还原更改 请勿关闭计算机 开不了机 这个问题怎么办...

    解析如下&#xff1a;1、长按电脑电源键直至关机&#xff0c;然后再按一次电源健重启电脑&#xff0c;按F8健进入安全模式2、安全模式下进入Windows系统桌面后&#xff0c;按住“winR”打开运行窗口&#xff0c;输入“services.msc”打开服务设置3、在服务界面&#xff0c;选中…...

    2022/11/19 21:17:18
  26. 错误使用 reshape要执行 RESHAPE,请勿更改元素数目。

    %读入6幅图像&#xff08;每一幅图像的大小是564*564&#xff09; f1 imread(WashingtonDC_Band1_564.tif); subplot(3,2,1),imshow(f1); f2 imread(WashingtonDC_Band2_564.tif); subplot(3,2,2),imshow(f2); f3 imread(WashingtonDC_Band3_564.tif); subplot(3,2,3),imsho…...

    2022/11/19 21:17:16
  27. 配置 已完成 请勿关闭计算机,win7系统关机提示“配置Windows Update已完成30%请勿关闭计算机...

    win7系统关机提示“配置Windows Update已完成30%请勿关闭计算机”问题的解决方法在win7系统关机时如果有升级系统的或者其他需要会直接进入一个 等待界面&#xff0c;在等待界面中我们需要等待操作结束才能关机&#xff0c;虽然这比较麻烦&#xff0c;但是对系统进行配置和升级…...

    2022/11/19 21:17:15
  28. 台式电脑显示配置100%请勿关闭计算机,“准备配置windows 请勿关闭计算机”的解决方法...

    有不少用户在重装Win7系统或更新系统后会遇到“准备配置windows&#xff0c;请勿关闭计算机”的提示&#xff0c;要过很久才能进入系统&#xff0c;有的用户甚至几个小时也无法进入&#xff0c;下面就教大家这个问题的解决方法。第一种方法&#xff1a;我们首先在左下角的“开始…...

    2022/11/19 21:17:14
  29. win7 正在配置 请勿关闭计算机,怎么办Win7开机显示正在配置Windows Update请勿关机...

    置信有很多用户都跟小编一样遇到过这样的问题&#xff0c;电脑时发现开机屏幕显现“正在配置Windows Update&#xff0c;请勿关机”(如下图所示)&#xff0c;而且还需求等大约5分钟才干进入系统。这是怎样回事呢&#xff1f;一切都是正常操作的&#xff0c;为什么开时机呈现“正…...

    2022/11/19 21:17:13
  30. 准备配置windows 请勿关闭计算机 蓝屏,Win7开机总是出现提示“配置Windows请勿关机”...

    Win7系统开机启动时总是出现“配置Windows请勿关机”的提示&#xff0c;没过几秒后电脑自动重启&#xff0c;每次开机都这样无法进入系统&#xff0c;此时碰到这种现象的用户就可以使用以下5种方法解决问题。方法一&#xff1a;开机按下F8&#xff0c;在出现的Windows高级启动选…...

    2022/11/19 21:17:12
  31. 准备windows请勿关闭计算机要多久,windows10系统提示正在准备windows请勿关闭计算机怎么办...

    有不少windows10系统用户反映说碰到这样一个情况&#xff0c;就是电脑提示正在准备windows请勿关闭计算机&#xff0c;碰到这样的问题该怎么解决呢&#xff0c;现在小编就给大家分享一下windows10系统提示正在准备windows请勿关闭计算机的具体第一种方法&#xff1a;1、2、依次…...

    2022/11/19 21:17:11
  32. 配置 已完成 请勿关闭计算机,win7系统关机提示“配置Windows Update已完成30%请勿关闭计算机”的解决方法...

    今天和大家分享一下win7系统重装了Win7旗舰版系统后&#xff0c;每次关机的时候桌面上都会显示一个“配置Windows Update的界面&#xff0c;提示请勿关闭计算机”&#xff0c;每次停留好几分钟才能正常关机&#xff0c;导致什么情况引起的呢&#xff1f;出现配置Windows Update…...

    2022/11/19 21:17:10
  33. 电脑桌面一直是清理请关闭计算机,windows7一直卡在清理 请勿关闭计算机-win7清理请勿关机,win7配置更新35%不动...

    只能是等着&#xff0c;别无他法。说是卡着如果你看硬盘灯应该在读写。如果从 Win 10 无法正常回滚&#xff0c;只能是考虑备份数据后重装系统了。解决来方案一&#xff1a;管理员运行cmd&#xff1a;net stop WuAuServcd %windir%ren SoftwareDistribution SDoldnet start WuA…...

    2022/11/19 21:17:09
  34. 计算机配置更新不起,电脑提示“配置Windows Update请勿关闭计算机”怎么办?

    原标题&#xff1a;电脑提示“配置Windows Update请勿关闭计算机”怎么办&#xff1f;win7系统中在开机与关闭的时候总是显示“配置windows update请勿关闭计算机”相信有不少朋友都曾遇到过一次两次还能忍但经常遇到就叫人感到心烦了遇到这种问题怎么办呢&#xff1f;一般的方…...

    2022/11/19 21:17:08
  35. 计算机正在配置无法关机,关机提示 windows7 正在配置windows 请勿关闭计算机 ,然后等了一晚上也没有关掉。现在电脑无法正常关机...

    关机提示 windows7 正在配置windows 请勿关闭计算机 &#xff0c;然后等了一晚上也没有关掉。现在电脑无法正常关机以下文字资料是由(历史新知网www.lishixinzhi.com)小编为大家搜集整理后发布的内容&#xff0c;让我们赶快一起来看一下吧&#xff01;关机提示 windows7 正在配…...

    2022/11/19 21:17:05
  36. 钉钉提示请勿通过开发者调试模式_钉钉请勿通过开发者调试模式是真的吗好不好用...

    钉钉请勿通过开发者调试模式是真的吗好不好用 更新时间:2020-04-20 22:24:19 浏览次数:729次 区域: 南阳 > 卧龙 列举网提醒您:为保障您的权益,请不要提前支付任何费用! 虚拟位置外设器!!轨迹模拟&虚拟位置外设神器 专业用于:钉钉,外勤365,红圈通,企业微信和…...

    2022/11/19 21:17:05
  37. 配置失败还原请勿关闭计算机怎么办,win7系统出现“配置windows update失败 还原更改 请勿关闭计算机”,长时间没反应,无法进入系统的解决方案...

    前几天班里有位学生电脑(windows 7系统)出问题了&#xff0c;具体表现是开机时一直停留在“配置windows update失败 还原更改 请勿关闭计算机”这个界面&#xff0c;长时间没反应&#xff0c;无法进入系统。这个问题原来帮其他同学也解决过&#xff0c;网上搜了不少资料&#x…...

    2022/11/19 21:17:04
  38. 一个电脑无法关闭计算机你应该怎么办,电脑显示“清理请勿关闭计算机”怎么办?...

    本文为你提供了3个有效解决电脑显示“清理请勿关闭计算机”问题的方法&#xff0c;并在最后教给你1种保护系统安全的好方法&#xff0c;一起来看看&#xff01;电脑出现“清理请勿关闭计算机”在Windows 7(SP1)和Windows Server 2008 R2 SP1中&#xff0c;添加了1个新功能在“磁…...

    2022/11/19 21:17:03
  39. 请勿关闭计算机还原更改要多久,电脑显示:配置windows更新失败,正在还原更改,请勿关闭计算机怎么办...

    许多用户在长期不使用电脑的时候&#xff0c;开启电脑发现电脑显示&#xff1a;配置windows更新失败&#xff0c;正在还原更改&#xff0c;请勿关闭计算机。。.这要怎么办呢&#xff1f;下面小编就带着大家一起看看吧&#xff01;如果能够正常进入系统&#xff0c;建议您暂时移…...

    2022/11/19 21:17:02
  40. 还原更改请勿关闭计算机 要多久,配置windows update失败 还原更改 请勿关闭计算机,电脑开机后一直显示以...

    配置windows update失败 还原更改 请勿关闭计算机&#xff0c;电脑开机后一直显示以以下文字资料是由(历史新知网www.lishixinzhi.com)小编为大家搜集整理后发布的内容&#xff0c;让我们赶快一起来看一下吧&#xff01;配置windows update失败 还原更改 请勿关闭计算机&#x…...

    2022/11/19 21:17:01
  41. 电脑配置中请勿关闭计算机怎么办,准备配置windows请勿关闭计算机一直显示怎么办【图解】...

    不知道大家有没有遇到过这样的一个问题&#xff0c;就是我们的win7系统在关机的时候&#xff0c;总是喜欢显示“准备配置windows&#xff0c;请勿关机”这样的一个页面&#xff0c;没有什么大碍&#xff0c;但是如果一直等着的话就要两个小时甚至更久都关不了机&#xff0c;非常…...

    2022/11/19 21:17:00
  42. 正在准备配置请勿关闭计算机,正在准备配置windows请勿关闭计算机时间长了解决教程...

    当电脑出现正在准备配置windows请勿关闭计算机时&#xff0c;一般是您正对windows进行升级&#xff0c;但是这个要是长时间没有反应&#xff0c;我们不能再傻等下去了。可能是电脑出了别的问题了&#xff0c;来看看教程的说法。正在准备配置windows请勿关闭计算机时间长了方法一…...

    2022/11/19 21:16:59
  43. 配置失败还原请勿关闭计算机,配置Windows Update失败,还原更改请勿关闭计算机...

    我们使用电脑的过程中有时会遇到这种情况&#xff0c;当我们打开电脑之后&#xff0c;发现一直停留在一个界面&#xff1a;“配置Windows Update失败&#xff0c;还原更改请勿关闭计算机”&#xff0c;等了许久还是无法进入系统。如果我们遇到此类问题应该如何解决呢&#xff0…...

    2022/11/19 21:16:58
  44. 如何在iPhone上关闭“请勿打扰”

    Apple’s “Do Not Disturb While Driving” is a potentially lifesaving iPhone feature, but it doesn’t always turn on automatically at the appropriate time. For example, you might be a passenger in a moving car, but your iPhone may think you’re the one dri…...

    2022/11/19 21:16:57