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

Android Jetpack - Navigation 组件:进行应用程序导航

在这里插入图片描述

一. Navigation 组件的介绍

1.1 什么是 Navigation 组件

  • Navigation 组件是一种 Android Jetpack 库,它可以帮助开发者轻松地实现应用程序中的导航功能。导航组件包含多个类和组件,包括导航图、目的地、导航控制器等,可以帮助我们管理应用程序中的页面导航和任务导航。通过使用 Navigation 组件,我们可以更加方便地实现应用程序的导航功能,同时也可以提高应用程序的用户体验。在本篇文章中,我们将介绍如何使用 Navigation 组件来实现应用程序导航,并提供一些示例和更多的扩展功能。

1.2 Navigation 组件的优势

  • Navigation 组件可以轻松实现应用程序中的导航,包括页面之间的转换和应用程序内部的导航。
  • Navigation 组件可以提高应用程序的可维护性和可扩展性,因为它们使得应用程序的结构更加清晰,并且可以更容易地添加新的功能和页面。
  • Navigation 组件可以提供一致的用户体验,因为它们使用了标准的导航模式和动画效果。
  • Navigation 组件可以帮助开发人员更快地构建应用程序,因为它们提供了许多常见的导航模式和功能,可以直接使用或进行修改。
  • Navigation 组件可以提高应用程序的可测试性,因为它们使得页面之间的导航和状态转换更加明确和可控。

1.3 Navigation 组件主要由3个部分组成:

  • NavHost:用来嵌入导航流程的容器,一般使用FragmentContainerView
  • NavController:负责在NavHost内部处理导航事务的控制器,用于执行页面跳转、管理返回栈等。
  • NavGraph:描述Fragment之间导航关系的资源文件,在其中定义页面之间的转跳、动画等。一般放在res/navigation/目录下。

简而言之,Navigation组件通过在NavHost中使用NavGraph来描述Fragment导航路径与关系,然后由NavController来执行实际的导航工作,这样极大地简化了以往的页面跳转逻辑和回退栈管理流程。

二. Navigation 组件的基本使用

2.1 添加导航组件到项目中

  • 在项目的 build.gradle 文件中添加以下依赖:
dependencies {def nav_version = "2.5.3"implementation "androidx.navigation:navigation-fragment-ktx:$nav_version"implementation "androidx.navigation:navigation-ui-ktx:$nav_version"
}
  • 在布局文件中添加 NavHostFragment:
<androidx.fragment.app.FragmentContainerViewandroid:id="@+id/nav_host_fragment"android:name="androidx.navigation.fragment.NavHostFragment"android:layout_width="match_parent"android:layout_height="match_parent"app:navGraph="@navigation/nav_graph" />
  • 正确获取 NavController 对象 :

在 Activity 内使用 NavController 时,应在onCreate()中获取:

val navHostFragment = supportFragmentManager.findFragmentById(R.id.nav_host_fragment) as NavHostFragment
val navController = navHostFragment.navController
NavigationUI.setupActionBarWithNavController(this, navController)

而在 Fragment 内,应在onAttach()onViewCreate()中获取:

val navHostFragment = parentFragment as NavHostFragment
val navController = navHostFragment.navController

NavHost需要指定app:navGraph属性来关联一个导航图NavGraph,这决定了其中Fragment页面之间的导航关系和跳转路径。

NavControllerNavigation组件的控制中心,用于在NavHost内执行导航操作。可以在ActivityFragment中通过NavHostFragmentnavController属性获取对应的NavController实例。

常见的导航操作有:

  • 导航到目标目的地:navController.navigate(R.id.destination_id)
  • 回退一个目的地:navController.navigateUp()navController.popBackStack()
  • 回退到根目的地:navController.popBackStack(R.id.root_destination, false)

NavController还负责维护Fragment的回退栈,以及在按返回按钮时正确出栈,这大大简化了之前管理Fragment事务的复杂度。
通过NavHostNavController的配合,Navigation组件实现了在NavGraph中声明的导航逻辑和页面切换功能。这使Fragment之间的导航变得极为简单高效。开发者只需关注于定义NavGraph,并调用NavController中的导航方法即可实现页面跳转,其余的一切尽在Navigation组件的掌控之中。

2.2 创建导航图

  • 在XML文件中创建导航图:
<androidx.fragment.app.FragmentContainerViewandroid:id="@+id/nav_host_fragment"android:name="androidx.navigation.fragment.NavHostFragment"android:layout_width="match_parent"android:layout_height="match_parent"app:navGraph="@navigation/nav_graph" />
  • 在res文件夹下创建一个navigation文件夹,然后在该文件夹下创建一个nav_graph.xml文件,用于定义导航图的结构和内容:
<navigation xmlns:android="http://schemas.android.com/apk/res/android"xmlns:app="http://schemas.android.com/apk/res-auto"xmlns:tools="http://schemas.android.com/tools"android:id="@+id/nav_graph"app:startDestination="@id/firstFragment"><fragmentandroid:id="@+id/firstFragment"android:name="com.smallmarker.jetpackpractice.navigation.fragment.FirstFragment"android:label="First"tools:layout="@layout/fragment_first"><actionandroid:id="@+id/action_firstFragment_to_secondFragment"app:destination="@+id/secondFragment" /></fragment><fragmentandroid:id="@+id/secondFragment"android:name="com.smallmarker.jetpackpractice.navigation.fragment.SecondFragment"android:label="Second"tools:layout="@layout/fragment_second" /></navigation>

在导航图中,<fragment> 元素用于定义目的地,android:id属性用于指定目的地的唯一标识符,android:name 属性用于指定目的地的类名,android:label 属性用于指定目的地在应用程序中显示的标签名称。

<action> 元素用于定义动作,android:id 属性用于指定动作的唯一标识符,app:destination 属性用于指定动作要执行的目的地。

三. Navigation 组件的高级使用

3.1 深层链接

在 Android 中,深层链接是指将用户直接转到应用内特定目的地的链接。借助 Navigation 组件,您可以创建两种不同类型的深层链接:显式深层链接和隐式深层链接。

  • 创建显式深层链接:

显式深层链接是深层链接的一个实例,该实例使用 PendingIntent 将用户转到应用内的特定位置。例如,您可以在通知或应用 widget 中显示显式深层链接。

    val pendingIntent = NavDeepLinkBuilder(it).setGraph(R.navigation.nav_deep_link).setDestination(R.id.deepLinkFragment).setArguments(Bundle().apply {putInt("id", 1)}).setComponentName(DeepLinkActivity::class.java).createPendingIntent()val notification = NotificationCompat.Builder(it, "my_channel").setContentTitle("Title").setContentText("测试深层链接").setSmallIcon(R.mipmap.ic_launcher).setContentIntent(pendingIntent).build()NotificationManagerCompat.from(it).notify(Random.nextInt(10), notification)

该示例使用 NavDeepLinkBuilder 类构造 PendingIntent, 添加到通知中并发送,点击通知跳转指定页面。

  • 创建隐式深层链接:
<navigation xmlns:android="http://schemas.android.com/apk/res/android"xmlns:app="http://schemas.android.com/apk/res-auto"xmlns:tools="http://schemas.android.com/tools"android:id="@+id/nav_deep_link"app:startDestination="@id/deepLinkFragment"><fragmentandroid:id="@+id/deepLinkFragment"android:name="com.smallmarker.jetpackpractice.navigation.fragment.DeepLinkFragment"android:label="DeepLink"tools:layout="@layout/fragment_deep_link"><deepLink app:uri="example://deepLink/{id}" /></fragment></navigation>

如需启用隐式深层链接,您还必须向应用的 manifest.xml 文件中添加内容。将一个 <nav-graph> 元素添加到指向现有导航图的 activity,如以下示例所示。

<activityandroid:name=".navigation.DeepLinkActivity"android:exported="true"><nav-graph android:value="@navigation/nav_deep_link" />
</activity>

在这个例子中,我们定义了一个深度链接,它的 URI 是"example://deepLink/{id}",其中{itemId}是一个参数。当用户在浏览器或其他应用中点击这个链接时,Android 系统会自动打开我们的应用,并跳转到对应的页面,同时将参数传递给我们的应用。我们可以在目标页面中通过arguments来获取这个参数。

3.2 共享元素转场

  • 共享元素转场可以实现在不同ActivityFragment之间共享相同元素的动画效果,比如在列表页面点击某个item进入详情页面时,可以让这个item的图片或文字在两个页面之间平滑地过渡。以下是一个简单的实现示例:
  <!-- 在layout文件中定义共享元素的id --><ImageView android:id="@+id/image_view"android:layout_width="wrap_content"android:layout_height="wrap_content"android:transitionName="shared_element" />
  • 到 Fragment 目的地的共享元素过渡
val extras = FragmentNavigatorExtras(view1 to "shared_element")view.findNavController().navigate(R.id.confirmationAction, null, null, extras)
  • 到 Activity 目的地的共享元素过渡
  val option = ActivityOptionsCompat.makeSceneTransitionAnimation(activity, imageView, "shared_element")findNavController().navigate(R.id.shareElementDialog, null, null, ActivityNavigatorExtras(option))

共享元素以程序化方式提供,而不是通过导航 XML 文件提供。activityfragment 目的地各自都有 Navigator.Extras 接口的一个子类,它接受导航的附加选项,包括共享元素。您可以在调用 navigate() 时传递这些 Extras

3.3 导航图的动态构建- 动态构建导航图可以在运行时根据不同的条件创建不同的导航图,例如用户登录状态不同、权限不同等情况下展示不同的导航结构。

  • 下面是一个简单的动态构建导航图的示例:
  val navHostFragment = supportFragmentManager.findFragmentById(R.id.nav_host_fragment) as NavHostFragmentval navController = navHostFragment.navControllerval graph = navInflater.inflate(R.navigation.dynamic_nav_graph)if (isLoggedIn) {graph.startDestination = R.id.homeFragment} else {graph.startDestination = R.id.loginFragment}if (hasAdminPermissions) {val adminNode = NavGraphNavigator(navController.navigatorProvider.getNavigator(NavGraphNavigator::class.java)).createDestination()adminNode.id = R.id.adminFragmentadminNode.setClassName("com.example.app.AdminFragment")graph.addDestination(adminNode)graph.addEdge(R.id.homeFragment, R.id.adminFragment)}navController.graph = graph

在上面的示例中,我们首先获取到了当前的NavControllerNavInflater,然后通过NavInflater.inflate方法来加载我们的动态导航图。接着,我们根据不同的条件设置了导航图的起始目的地,并且在有管理员权限的情况下动态添加了一个目的地,并且添加了一条边来连接这个目的地和主页。最后,我们将构建好的导航图设置到NavController中即可。

四. 导航组件的最佳实践

4.1 使用<include>标签

  • 为每个模块定义单独的NavGraph在大型项目中,最好为每个功能模块定义自己的NavGraph,然后在根NavGraph中使用<include>标签将每个模块的NavGraph组合起来::
  <navigation xmlns:android="http://schemas.android.com/apk/res/android"xmlns:app="http://schemas.android.com/apk/res-auto"android:id="@+id/root_navigation"><include android:id="@+id/home_navigation"app:layout="@navigation/home_navigation" /><include android:id="@+id/profile_navigation"app:layout="@navigation/profile_navigation" />  </navigation>

4.1 使用 ViewModel 和 LiveData

  • 在 ViewModel 中使用 LiveData 对象来处理导航事件:
class MainViewModel : ViewModel() {private val navigateTo = MutableLiveData<NavDirections>()fun getNavigateTo(): LiveData<NavDirections> {return navigateTo}fun setNavigateTo(directions: NavDirections) {navigateTo.value = directions}}
  • 在 Fragment 中观察 LiveData 对象并处理导航事件:
    class MainFragment : Fragment() {override fun onCreate(savedInstanceState: Bundle?) {super.onCreate(savedInstanceState)viewModel.getNavigateTo().observe(this) {Navigation.findNavController(requireView()).navigate(it)}}fun clickJump() {viewModel.setNavigateTo(MainFragmentDirections.actionMainToNavigationActivity())}}

注意这里我们使用了 Safe Args 实现类型安全的导航,在目的地之间导航,官方也是建议使用 Safe Args Gradle 插件。此插件可生成简单的对象和构建器类,以便在目的地之间实现类型安全的导航。我们强烈建议您在导航以及在目的地之间传递数据时使用 Safe Args
如需将 Safe Args 添加到您的项目,请在顶层 build.gradle 文件中包含以下 classpath:

buildscript {dependencies {def nav_version = "2.5.3"classpath("androidx.navigation:navigation-safe-args-gradle-plugin:$nav_version")}
}

然后再将以下行添加到应用或模块的 build.gradle 文件中:

plugins {id("androidx.navigation.safeargs.kotlin")
}

五. 总结

5.1 导航组件的优势和适用场景:

优势适用场景
1. 提供一致的导航体验适用于需要在应用中引入多个页面的场景
2. 简化导航逻辑适用于需要在应用中进行复杂的导航操作的场景
3. 可自定义外观和行为适用于需要根据应用需求自定义导航栏的场景
4. 支持深层链接适用于需要在应用中支持深层链接的场景

5.2 导航组件的最佳实践- 在使用导航组件时,应该尽量减少手动操作 Fragment 事务,而是使用导航组件提供的 API 进行操作,以避免出现不必要的错误。

  • 在设计导航图时,应该尽量将功能相似的页面放在同一个导航图中,以便于管理和维护。
  • 在使用 Safe Args 插件传递参数时,应该尽量使用安全的类型,以避免出现类型转换错误。

以上就是对 Android Navigation 的探索与实践的过程,上述示例 + 扩展(结合 BottomNavigationView 和 DrawerLayout)请参考 https://github.com/smallmarker/JetPackPractice

相关文章:

Android Jetpack - Navigation 组件:进行应用程序导航

一. Navigation 组件的介绍 1.1 什么是 Navigation 组件 Navigation 组件是一种 Android Jetpack 库&#xff0c;它可以帮助开发者轻松地实现应用程序中的导航功能。导航组件包含多个类和组件&#xff0c;包括导航图、目的地、导航控制器等&#xff0c;可以帮助我们管理应用程…...

MySQL的binlog原理和它的几种使用方法

MySQL中的二进制日志&#xff08;binlog&#xff09;是一种用于记录数据库操作的日志文件&#xff0c;它可以记录MySQL服务器接收到的所有修改数据库的语句&#xff0c;例如INSERT、UPDATE和DELETE等语句。二进制日志对于备份和恢复数据库、复制数据库和进行数据分析等操作非常…...

40岁以上的程序员还容易找到工作吗?聊聊我自己的亲身经历

今天我们来讨论一个比较热门的话题&#xff0c;那就是程序员。如果到了40岁以上还容易找到工作吗&#xff1f;这个问题呢&#xff0c;其实是一个非常现实的问题&#xff0c;也是我们程序员非常关心的一个问题。因为我们每一个程序员&#xff0c;他都会有到40岁的那一天。 首先…...

Class类

package com.hspedu.reflection.class_;import com.hspedu.Cat;import java.util.ArrayList;/*** author 韩顺平* version 1.0* 对Class类特点的梳理*/ public class Class01 {public static void main(String[] args) throws ClassNotFoundException {//看看Class类图//1. Cla…...

Python小姿势 - 可选知识点:

可选知识点&#xff1a; 列表推导式 列表和字典推导式 字典推导式 生成器表达式 带条件的生成器表达式 解析XML 解析JSON 使用Requests和BeautifulSoup爬虫 Python并发编程 Python多线程编程 Python多进程编程 Python异步编程 Python装饰器 Python闭包 Python模块化 Python类和…...

Javaee Spring的AOP简介

一.Spring的AOP简介 1.1 什么是AOP AOP 为 Aspect Oriented Programming 的缩写&#xff0c;意思为面向切面编程&#xff0c;是通过预编译方式和运行期动态代 理实现程序功能的统一维护的一种技术。AOP 是 OOP 的延续&#xff0c;是软件开发中的一个热点&#xff0c;也是…...

基于ansible初始化linux服务器基础环境。

大家好&#xff0c;今天我要和大家分享一个关于搭建centos环境的新方法。 以前我们经常会看到一些文章介绍如何搭建centos环境&#xff0c;但很多时候都会出现一些问题。不过现在有了一种新的方法&#xff0c;就是使用ansible脚本来实现。 虽然这种方法仅适用于centos7&#…...

leetcode-数据库题

提示&#xff1a;文章写完后&#xff0c;目录可以自动生成&#xff0c;如何生成可参考右边的帮助文档 文章目录 175. 组合两个表176. 第二高的薪水177. 第N高的薪水178. 分数排名181. 超过经理收入的员工182. 查找重复的电子邮箱183. 从不订购的客户 175. 组合两个表 select p…...

[元来学NVMe协议] NVMe IO 指令集(NVM 指令集)| Flush 命令

声明 主页:元存储的博客_CSDN博客 依公开知识及经验整理,如有误请留言。 个人辛苦整理,付费内容,禁止转载。 内容摘要 前言 NVMe2.0 定义的三类命令集: 管理命令集、IO命令集、Fabrics命令集 Admin Command Set (管理命令集):用于控制器的管理,如创建/销毁IO提交队列…...

信息的相关性和冗余度:信息在整个文明中的作用

文章目录 I 古埃及的象形文字1.1 罗塞塔石碑1.2 古埃及文字音节和希腊字母的对应表1.3 破解古埃及文字 I 古埃及的象形文字 1.1 罗塞塔石碑 这个石碑是在公元前196年埃及国王托勒密五世加冕一周年的诏书。 在此前大约一百年&#xff0c;埃及已经被来自希腊北方城邦的亚历山大…...

python数据结构与算法-动态规划(最长公共子序列)

一、最长公共子序列问题 1、问题概念 一个序列的子序列是在该序列中删去若干元素后得 到的序列。 例如&#xff1a;"ABCD”和“BDF”都是“ABCDEFG”的子序列。 最长公共子序列(LCS) 问题: 给定两个序列X和Y&#xff0c;求X和Y长度最大的公共子字列。 例:X"ABBCBDE”…...

Java版企业电子招投标系统源码 Spring Cloud+Spring Boot 电子招标采购系统功能清单

一、立项管理 1、招标立项申请 功能点&#xff1a;招标类项目立项申请入口&#xff0c;用户可以保存为草稿&#xff0c;提交。 2、非招标立项申请 功能点&#xff1a;非招标立项申请入口、用户可以保存为草稿、提交。 3、采购立项列表 功能点&#xff1a;对草稿进行编辑&#x…...

【c语言】函数的基本概念 | 函数堆栈调用原理

创作不易&#xff0c;本篇文章如果帮助到了你&#xff0c;还请点赞支持一下♡>&#x16966;<)!! 主页专栏有更多知识&#xff0c;如有疑问欢迎大家指正讨论&#xff0c;共同进步&#xff01; 给大家跳段街舞感谢支持&#xff01;ጿ ኈ ቼ ዽ ጿ ኈ ቼ ዽ ጿ ኈ ቼ ዽ ጿ…...

Vue.prototype 详解及使用

前言&#xff1a; 我们可能会在很多组件里用到数据/实用工具&#xff0c;但是不想污染全局作用域。这种情况下&#xff0c;可以通过在原型上定义它们使其在每个 Vue 的实例中可用。 1. 基本示例 在main.js中添加一个变量到 Vue.prototype Vue.prototype.$appName My App这…...

音视频八股文(3)--ffmpeg常见命令(2)

07-ffplay命令播放媒体 播放本地文件 播放本地 MP4 视频文件 test.mp4 的命令&#xff0c;从第 2 秒位置开始播放&#xff0c;播放时长为 10 秒&#xff0c;并且在窗口标题中显示 “test time”&#xff1a; ffplay -window_title "test time" -ss 2 -t 10 -autoe…...

使用bert4keras出现的问题(Process finished with exit code -1073741819 (0xC0000005))

1、环境 python 3.7.12 tensorflow 1.15 keras 2.3.1 bert4keras 0.9.7 protobuf 3.19.0 numpy 1.16.5 2、出现问题 numpy版本不兼容问题所以你就直接按照我的版本就可以了&#xff08;numpy 1.16.5&#xff09; Process finished with exit code -1073741819 (0xC0000005) …...

python协程实战

协程简介 协程(Coroutine)又称微线程、纤程&#xff0c;协程不是进程或线程&#xff0c;其执行过程类似于 Python 函数调用&#xff0c;Python 的 asyncio 模块实现的异步IO编程框架中&#xff0c;协程是对使用 async 关键字定义的异步函数的调用; 一个进程包含多个线程,类似…...

【论文笔记】VideoGPT: Video Generation using VQ-VAE and Transformers

论文标题&#xff1a;VideoGPT: Video Generation using VQ-VAE and Transformers 论文代码&#xff1a;https://wilson1yan. github.io/videogpt/index.html. 论文链接&#xff1a;https://arxiv.org/abs/2104.10157 发表时间&#xff1a; 2021年9月 Abstract 作者提出了…...

scala之基础面向对象

scala 既是面向对象 也是函数式编程 从Java 发展而来&#xff0c;依赖JVM环境 一、 scala 在linux中运行 scala 模式中直接编写运行 scala文件&#xff0c;load执行 scala编译程序 编译 运行 scala java 二、scala 数据类型 基础数据类型 val 不可变变量 函数式编程 …...

Qt5.12实战之多线程编程概念

1.为什么要使用多线程? a. 基于线程,同时处理多个任务,软件响应更灵敏 b.充分利用CPU的多核心功能增加应用运行效率 c.多线程在同一进程间使用共享通信更加高效 d.多个线程之间进行切换比多个进程之间进行切换,线程开销更少. 2.操作系统与进程关系 a. MS-DOS系统 属于单进程…...

格式化数据恢复怎么做?超实用的3种方法在这!

案例&#xff1a;格式化数据怎么恢复 【我的电脑前段时间中病毒了&#xff0c;无奈之下我只能将其格式化&#xff0c;但是很多重要的文件和图片之类的也一起被删除了&#xff0c;有什么方法可以恢复这些格式化的数据吗&#xff1f;非常着急&#xff01;】 格式化数据恢复&…...

【Java|golang】1105. 填充书架---动态规划

给定一个数组 books &#xff0c;其中 books[i] [thicknessi, heighti] 表示第 i 本书的厚度和高度。你也会得到一个整数 shelfWidth 。 按顺序 将这些书摆放到总宽度为 shelfWidth 的书架上。 先选几本书放在书架上&#xff08;它们的厚度之和小于等于书架的宽度 shelfWidt…...

linux基础命令

linux基础命令 一、linux命令 熟悉账务linux命令对运维的好处是巨大的&#xff0c;只有熟悉了命令咱们在运维的操作上才能如鱼得水。 系统信息 arch #显示机器的处理器架构(1) uname -m #显示机器的处理器架构(2) uname -r #显示正在使用的内核版本 dmidecode -q …...

【三十天精通Vue 3】 第十八天 Vue 3的国际化详解

✅创作者&#xff1a;陈书予 &#x1f389;个人主页&#xff1a;陈书予的个人主页 &#x1f341;陈书予的个人社区&#xff0c;欢迎你的加入: 陈书予的社区 &#x1f31f;专栏地址: 三十天精通 Vue 3 文章目录 引言一、Vue 3 国际化概述1.1 国际化的概念1.2 国际化的作用1.3 V…...

02 - 学会提问

学会提问 一、引言 1.1 GPT简介 GPT&#xff08;Generative Pre-trained Transformer&#xff09;是一种基于Transformer架构的大型预训练语言模型。 凭借其强大的文本生成、理解和处理能力&#xff0c;GPT已在诸如自然语言处理、机器翻译、文本摘要等多个领域取得了显著的…...

Java经典的Main方法面试题

mian方法是做什么用的&#xff1f; main方法是Java程序的入口方法&#xff0c;JVM在运行的时候会首先查找main方法不用main方法如何运行一个类&#xff1f; 不行&#xff0c;没有main方法我们不能运行Java类 在Java7之前&#xff0c;你可以通过使用静态初始化运行Java类。但是&…...

世界大学电子电气工程TOP10,国内大学哪家强?

EE究竟是什么专业 ? 在中国&#xff0c;工程系中跟电相关的专业&#xff0c;一般都切分得非常细。有电子工程、电气工程、通信工程、信息工程、自动化、测控仪器等。但在国外&#xff0c;一般把这些领域都归类到 Electrical Engineering 中&#xff0c;也就是我们常说的EE。 …...

5.3 牛顿-科茨公式

学习目标&#xff1a; 理解微积分基础知识&#xff0c;例如导数和微分的概念。学习牛顿-科茨公式的推导过程。这个公式实际上是使用泰勒公式对被积函数进行展开&#xff0c;并使用微积分的基本原理进行简化得到的。学习如何使用牛顿-科茨公式进行数值积分。这通常涉及到将被积…...

全注解下的SpringIoc 续2-bean的生命周期

spring中bean的生命周期 上一个小节梳理了一下Spring Boot的依赖注入的基本知识&#xff0c;今天来梳理一下spring中bean的生命周期。 下面&#xff0c;让我们一起看看bean在IOC容器中是怎么被创建和销毁的。 bean的生命周期大致分为四个部分&#xff1a; #mermaid-svg-GFXNEU…...

【VQ-VAE代码实战】Neural Discrete Representation Learning

【VQ-VAE代码实战】Neural Discrete Representation Learning 0、前言1、简介2、Basic IdeaLoss3、代码Load DataVector Quantizer LayerEncoder & Decoder ArchitectureTrainPlot LossView ReconstructionsView EmbeddingReference0、前言 论文地址:基于神经网络的,离散…...