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

Java 基础学习(四)操作数组、软件开发管理

1 操作数组

1.1.1 System.arraycopy 方法用于数组复制

当需要将一个数组的元素复制到另一个数组中时,可以使用System.arraycopy方法。它提供了一种高效的方式来复制数组的内容,避免了逐个元素赋值的繁琐过程。相对于使用循环逐个元素赋值的方式,System.arraycopy方法在底层使用了系统级的内存复制操作,因此在处理大型数组时可以更高效地完成复制操作,从而提高性能。使用System.arraycopy方法进行复制时,原始数组的数据将保持不变。这对于需要在不修改原数组的情况下进行数组复制的场景非常有用,如在并发环境中操作数组时可以保证数据的一致性。

使用 System.arraycopy( )方法可以简单的实现数组复制,语法如下:

其中:

  • src:源数组
  • srcPos:源数组中的起始位置
  • dest:目标数组
  • destPos:目标数组中的起始位置
  • length:要复制的数组元素的数量

System.arraycopy( )方法可以直接改变目标数组的内容,查看如下代码:

 上述代码的效果如下图所示:

 

1.1.2 Arrays.copyOf方法用于数组复制

System.arraycopy是一个底层的系统级方法,用于在两个数组之间进行元素的复制。它需要手动指定源数组、源数组的起始位置、目标数组、目标数组的起始位置以及要复制的元素个数。

而Arrays.copyOf方法则是在System.arraycopy的基础上进行了封装,提供了更简单的使用方式。它只需要指定源数组和新数组的长度即可,无需关心起始位置和元素个数,它会自动根据长度进行截取或填充默认值。这使得数组复制变得更加便捷和易于理解。

使用Arrays.copyOf方法进行数组复制的语法如下:

类型[ ]  newArray  = Arrays.copyOf ( 类型[ ]  original , int newLength );

其中,originalArray表示源数组,newLength表示新数组的长度。方法会创建一个新的数组,并将源数组的元素复制到新数组中。

需要注意的是,如果newLength小于源数组的长度,将会截取源数组的前newLength个元素进行复制;如果newLength大于源数组的长度,新数组将会以源数组的元素为基础,后面填充默认值(对于基本数据类型,填充0;对于引用数据类型,填充null)以达到指定的长度。

下面是一个示例:

int[] originalArray = {1, 2, 3, 4, 5};
int newLength = originalArray.length * 2; // 扩容为原数组长度的两倍
int[] newArray = Arrays.copyOf(originalArray, newLength);

在上述示例中,originalArray是原始数组,newLength是新数组的长度,通过将原数组复制到新数组中来实现扩容。

需要注意的是,在扩容数组时,原数组中的元素将被复制到新数组中,但原数组本身并不会发生改变。因此,如果需要使用扩容后的数组,应该使用新数组的引用,也就是替换原数组。

有需求如下:

1、创建一个长度为 10 的数组,并在数组内放置10个取值在 0 到 99 之间(包含0,包含99)的随机整数作为数组内容;

2、查询出数组中的最大值并输出;

3、将数组的长度扩容为 11,将查询到的数组最大值作为数组的最后一个元素

4、打印扩容后的数组元素,效果如下图:

 代码示意如下:

package summit_01;
import java.util.Arrays;
import java.util.Random;
public class ArrayCopyDemo1 {public static void main(String[] args) {// 生成随机数的工具Random ran = new Random();int[] array = new int[10];for (int i = 0; i < array.length; i++){array[i] = ran.nextInt(100);}// 输出数组中的元素System.out.println("数组中的数据为: "+Arrays.toString(array));// 查询数组中的最大值int max = -1;for (int i = 0; i < array.length; i++){if (max < array[i]){max = array[i];}}System.out.println("最大值是:"+max);// 复制数组int[] newArray = Arrays.copyOf(array, 11);newArray[10] = max;// 输出新的数组System.out.println("新数组中的数据为:"+Arrays.toString(newArray));}
}

1.2.1 数组的排序

排序是数组最常用的一类算法,用于将数组中的元素按照从小到大或从大到小的顺序重新排列。常用的排序算法包括插入排序、冒泡排序、快速排序等。

对于元素较多的数组,排序算法的优劣至关重要。一般情况下,通过排序过程中数组元素的交换次数来衡量排序算法的优劣。

1.2.2 冒泡排序法

冒泡排序(Bubble Sort)是一种简单的排序算法,它通过不断比较相邻的元素并交换位置来将较大的元素逐步"冒泡"到数组的末尾。它的基本思想是从数组的第一个元素开始,依次比较相邻的两个元素的大小,如果前一个元素大于后一个元素,则交换它们的位置,直到整个数组排序完成。

具体的冒泡排序算法步骤如下:

  • 从数组的第一个元素开始,将当前元素与下一个元素进行比较
  • 如果当前元素大于下一个元素,则交换它们的位置
  • 继续比较下一个相邻的元素,重复步骤2,直到最后一个元素
  • 重复以上步骤,每次循环将最大的元素"冒泡"到数组的末尾
  • 重复执行多次循环,每次循环都将一个最大的元素放到正确的位置,直到整个数组排序完成

冒泡排序的时间复杂度为O(n^2),其中n是数组的长度。它是一种简单但效率较低的排序算法,在处理小规模数据或者用于教学目的时较为常见。

比如有数组,包含7个整数数值,元素的初始存储顺序为 89、50、84、57、61、20、70。如果使用冒泡排序算法实现升序排列:

第一轮:找到最大的数移动到最后

  • 第一个位置与第二个位置的元素比较:89与50进行比较,由于89大于50,则两个数交换顺序
  • 第二个位置与第三个位置的元素比较:此时第二个位置的元素时89,大于第三个位置的84,二者交换
  • 第三个位置与第四个位置的元素比较,以此类推
  • 一轮比较完毕,最大的89被“冒泡”移动到最后

第二轮:在剩下元素里,找到最大的数并移动到剩下元素的最后(除去最后一个元素89)

第三轮、第四轮,以此类推下去,一共需要进行7轮。

比较的过程如下图所示:

 

1.2.3 【案例】冒泡排序算法实现

有一个长度为 10 的整型数组,元素均为0-100之间的整数。使用冒泡排序算法将数组按照升序排列,并输出排序的过程以及结果。效果如下图所示:

 代码示意如下:

package summit_01;
import java.util.Arrays;
public class BubbleSortDemo1 {public static void main(String[] args) {// 初始数组int[] array = new int[]{8, 54, 17, 11, 97, 68, 72, 75, 22, 75};System.out.println(Arrays.toString(array));// 冒泡排序int size = array.length;System.out.println("----------冒泡排序 开始----------");// 访问数组中每个元素的循环for (int i = 0; i < size - 1; i++) {// 比较数组中每个元素的循环for (int j = 0; j < size - i - 1; j++) {// 比较两个相邻的元素if (array[j] > array[j + 1]) {// 换位int temp = array[j];array[j] = array[j + 1];array[j + 1] = temp;}}System.out.println(Arrays.toString(array));}System.out.println("----------冒泡排序 结束----------");// 输出排序结果System.out.println(Arrays.toString(array));}
}

1.2.4 Arrays.sort方法用于数组排序

Arrays.sort是Java中java.util.Arrays类提供的一个静态方法,用于对数组进行排序。它使用的是优化后的快速排序(QuickSort)算法,对于大多数数据集合具有较好的性能。

Arrays.sort方法有多个重载版本,可以对不同类型的数组进行排序,包括基本数据类型和引用类型。它的基本语法如下:

public static void sort(int[] array)

其中,array是待排序的整型数组。该方法会对数组进行升序排序,即从小到大排列。

除了针对整型数组的排序,Arrays.sort还支持对其他类型的数组进行排序,例如char[]、double[]、String[]等等。

下面是一个使用Arrays.sort方法对整型数组进行排序的示例代码:

import java.util.Arrays;
public class ArraySorting {public static void main(String[] args) {int[] array = {5, 2, 8, 12, 1, 6};Arrays.sort(array);System.out.println("排序结果:");for (int i=0; i<array.lenght; i++) {System.out.print(array[i] + " ");}}
}

在上述代码中,我们定义了一个整型数组array,并使用Arrays.sort对数组进行排序。最后打印排序结果。

需要注意的是,Arrays.sort方法会直接修改原始数组,而不是返回一个新的排序后的数组。如果需要保留原数组的副本并进行排序,可以先使用Arrays.copyOf方法创建一个副本,然后对副本进行排序。

1.3.1 String底层是字符数组

在Java中,String类底层使用了一个字符数组来存储字符串中的字符。每个String对象都包含一个名为"value"的属性,该属性是一个char类型的数组,用于实际存储字符串的内容。

 

String类提供了一些方法,用于方便地操作字符数组和字符串之间的转换。通过这些方法,我们可以将字符存储到字符串中,也可以从字符串中获取字符数组,实现字符串和字符数组之间的相互转化。

例如,可以使用String的toCharArray()方法将字符串转换为一个字符数组,示例如下:

String str = "Hello";
char[] charArray = str.toCharArray(); // 将字符串转换为字符数组
for (int i=0; i<charArray.length; i++) {System.out.println(charArry[i]); // 输出每个字符
}

同样地,可以使用String的构造函数或者valueOf()方法将一个字符数组转换为字符串,示例如下:

char[] charArray = {'H', 'e', 'l', 'l', 'o'};
String str = new String(charArray); // 将字符数组转换为字符串
System.out.println(str); // 输出字符串 "Hello"

这些方法提供了便捷的方式来在字符串和字符数组之间进行转换,使得我们可以根据需要灵活地操作字符串的内容。

2 软件开发管理

2.1.1 软件生命周期概述

软件产品的生命周期是指从设计该产品的构想开始,到软件需求的确定、软件设计、软件实现、产品测试与验收、投入使用以及产品版本的不断更新,到最终该产品被市场淘汰的全过程。

软件生命周期这个概念从时间的角度将软件的开发和维护的复杂过程分解为了若干个阶段,每个阶段都完成特定的相对独立的任务。

2.1.2 传统软件生命周期

在传统的软件工程中,软件产品的生命周期一般可以划分为6个阶段,如图所示。

 

1、可行性研究。可行性研究就是指在项目进行开发之前,根据项目发起文件和实际情况,对该项目是否能在特定的资源、时间等制约条件下完成做出评估,并且确定它是否值得去开发。简单的说,可行性研究要回答“软件是否值得做”的问题。本阶段代表产物是《可行性研究报告》。

2、需求分析:需求分析是相关人员经过深入细致的调研和分析,准确理解用户和项目的功能、性能、可靠性等具体要求,将用户非形式的需求表述转化为完整的需求定义,从而确定系统必须做什么的过程。简单的说,需求分析要回答“软件必须做什么”的问题。本阶段代表产物是《需求规格说明书》。

3、软件设计:软件设计是软件开发过程中的重要阶段,在此阶段中,开发人员将集中研究如何把需求规格说明书里归纳的分析模型转换为可行的设计模型,并将解决方案记录到相关的设计文档中。实际上,软件设计的目标就是要回答“怎么做”才能实现软件系统的问题。本阶段代表产物是《软件设计说明书》。

4、编码:编码的过程就是把软件设计阶段得到的解决方案转化为可以在计算机上运行的软件产品的过程。本阶段的重要文档是《软件开发计划书》,代表产物是软件项目代码、《用户手册》、《部署文档》等。

5、软件测试:软件测试是发现软件中错误和缺陷的主要手段,为了保证软件产品的质量,软件开发人员通过软件测试发现产品中存在的问题,并对其进行及时的修改。可以说,软件测试的过程就是发现并改正软件缺陷的过程,本阶段的代表产物是《测试分析报告》。

6、软件维护:软件维护是软件产品生命周期的最后一个阶段。在产品交付并且投入使用之后,为了解决在使用过程中不断发现的各种问题,保证系统正常运行,同时使系统功能随着用户需求的更新而不断升级,软件维护的工作是非常必要的。

2.1.3 传统软件生命周期面临的挑战

传统软件生命周期面临的挑战如下:

  • 现实中很少有需求可以一次性或者在一段时间内完全定义清楚
  • 市场的变化可能导致在需求分析之后的阶段中产生需求的变更
  • 价值交付周期非常长

 

2.1.4 敏捷开发

敏捷开发以用户的需求进化为核心,采用迭代、循序渐进的方法进行软件开发。在敏捷开发中,软件项目在构建初期被切分成多个子项目,各个子项目的成果都经过测试,具备可视、可集成和可运行使用的特征。换言之,就是把一个大项目分为多个相互联系,但也可独立运行的小项目,并分别完成,在此过程中软件一直处于可使用状态。如下图所示:

 

2.1.5 敏捷开发框架

敏捷是一种灵活的项目管理方式,它是一套价值观和原则,有几种不同的敏捷开发框架用于应用敏捷原则。敏捷开发框架可以定义为用于实施敏捷开发并维护其价值的一种方法或一组技术和指南。

 

1、Scrum 是用于开发、交付和持续支持复杂产品的一个框架,是一个增量的、迭代的开发过程。在这个框架中,整个开发过程由若干个短的迭代周期组成。适用于单个团队的产品管理过程。它起源于软件开发项目,经过长期的实践现已适用于任何复杂的或是创新性的项目。

2、看板方法是为了解决“各个环节忙闲不匀,流程难以衔接”的问题而产生的,也就意味着它最大的优势是流程可视化。看板方法就像一个空货架,从视觉上对产品的流动进行追踪,以至于很容易发现瓶颈在哪里,空缺在哪里,生产流程是否衔接紧密等问题。看板方法有三个基本元素:板(Board)代表整个项目、列表或通道(List)代表一个分类,和卡(Card)代表进行的工作。它的流程大概是:把当前项目的任务项贴到白板上,每一个卡片代表一个任务,经过几个通道(完成部分任务进入下一个通道)后,即完成了当前的一个任务。

3、极限编程(Extreme programming,缩写为XP),是一种基于频繁交付周期的软件开发方法,是敏捷软件开发中应用最为广泛和最富有成效的几种方法之一。它的主要目标在于降低因需求变更而带来的成本。极限编程和传统方法相比,更强调可适应性而不是可预测性。且欣然接受变更,并关注锻造在项目周期内适应变化的能力。

2.1.6 DevOps

DevOps(Development和Operations的组合词)是一组过程、方法与系统的统称,用于促进开发(应用程序/软件工程)、技术运营和质量保障(QA)部门之间的沟通、协作与整合。

它是一种重视“软件开发人员(Dev)”和“IT运维技术人员(Ops)”之间沟通合作的文化、运动或惯例。透过自动化“软件交付”和“架构变更”的流程,来使得构建、测试、发布软件能够更加地快捷、频繁和可靠。

它的出现是由于软件行业日益清晰地认识到:为了按时交付软件产品和服务,开发和运维工作必须紧密合作。

 

2.2.1代码版本控制

在软件工程中,版本控制(也称为修订控制、源代码控制或源代码管理)是一类系统,负责管理对计算机程序、文档、大型网站或其他信息集合的更改。

在团队设计、开发和部署软件时,通常会在不同站点部署同一软件的多个版本,并且软件开发人员会同时进行更新。如下图所示:

 软件的一些错误或新特性通常只存在于某些版本中,为了定位和修复错误,能够检索并运行软件的不同版本是至关重要的。可能还需要同时开发软件的两个版本:例如,一个版本修复了错误,但没有新功能(分支),而另一个版本正在开发新功能(主干)。那么需要有效的工具能够对此进行管理。

 

2.2.2 Git

Git 是一种分布式版本控制系统,可以跟踪任何一组计算机文件的变化,通常用于在软件开发过程中协调协作开发源代码的程序员之间的工作。Git 最初由 Linus Torvalds 于 2005 年为 Linux 内核的开发而编写,其他内核开发人员为其初始开发做出了贡献。Git 是根据 GPL-2.0-only 许可证分发的免费开源软件。

 

2.2.3 GitHub

GitHub, Inc是一个使用 Git 进行软件开发和版本控制的互联网托管服务,它为每个项目提供 Git 的分布式版本控制以及访问控制、错误跟踪、软件功能请求、任务管理、持续集成和wiki。GitHub总部位于加利福尼亚州,自 2018 年起成为微软的子公司。截至 2023 年 1 月,GitHub 报告称拥有超过1亿开发人员和超过3.72亿个存储库,包括至少2800万个公共存储库。

 

2.2.4 Gitee

Gitee.com(码云) 是 OSCHINA.NET推出的代码托管平台,支持Git和SVN,提供免费的私有仓库托管,目前已有超过800万的开发者选择Gitee。

 

2.2.5【案例】Git使用实例

1、安装 Git

2、IDEA 关联 Git

2.3.1 软件开发云平台概述

软件开发云平台是指通过云服务的方式提供一站式云端DevOps平台。比如阿里云的“云效”:

 

2.3.2 阿里云云效

云效作为企业级一站式DevOps解决方案,提供从“需求->开发->测试->发布->运维”端到端的协同服务和研发工具,支持多种部署形态。

 

相关文章:

Java 基础学习(四)操作数组、软件开发管理

1 操作数组 1.1.1 System.arraycopy 方法用于数组复制 当需要将一个数组的元素复制到另一个数组中时&#xff0c;可以使用System.arraycopy方法。它提供了一种高效的方式来复制数组的内容&#xff0c;避免了逐个元素赋值的繁琐过程。相对于使用循环逐个元素赋值的方式&#x…...

git仓库如何撤销提交,恢复提交,重置版本命令

撤销提交&#xff1a; 要撤销最近一次提交&#xff08;未推送到远程仓库&#xff09;&#xff0c;可以使用以下命令&#xff1a; git reset HEAD^该命令将会把最后一次提交的修改从当前主分支中移除&#xff0c;并将这些修改的状态保留在本地工作目录中。 如果想要取消所有的…...

Java 基础学习(三)循环流程控制与数组

1 循环流程控制 1.1 循环流程控制概述 1.1.1 什么是循环流程控制 当一个业务过程需要多次重复执行一个程序单元时&#xff0c;可以使用循环流程控制实现。 Java中包含3种循环结构&#xff1a; 1.2 for循环 1.2.1 for循环基础语法 for循环是最常用的循环流程控制&#xff…...

别太担心,人类只是把一小部分理性和感性放到了AI里

尽管人工智能&#xff08;AI&#xff09;在许多方面已经取得了重大进展&#xff0c;但它仍然无法完全复制人类的理性和感性。AI目前主要侧重于处理逻辑和分析任务&#xff0c;而人类则具有更复杂的思维能力和情感经验。 人类已经成功地将一些可以数据化和程序化的理性和感性特征…...

最新AIGC创作系统ChatGPT系统源码+DALL-E3文生图+图片上传对话识图/支持OpenAI-GPT全模型+国内AI全模型

一、AI创作系统 SparkAi创作系统是基于ChatGPT进行开发的Ai智能问答系统和Midjourney绘画系统&#xff0c;支持OpenAI-GPT全模型国内AI全模型。本期针对源码系统整体测试下来非常完美&#xff0c;可以说SparkAi是目前国内一款的ChatGPT对接OpenAI软件系统。那么如何搭建部署AI…...

在centos7上源码安装nginx

1. 安装必要的编译工具和依赖项 在编译Nginx之前&#xff0c;你需要安装一些编译工具和依赖项。可以通过以下命令安装&#xff1a; yum install gcc-c pcre-devel zlib-devel make 2. 下载Nginx源代码 从Nginx官网下载最新的源代码。你可以使用wget命令来下载&#xff1a; …...

Html网页threejs显示obj,ply三维图像实例

程序示例精选 Html网页threejs显示obj,ply三维图像实例 如需安装运行环境或远程调试&#xff0c;见文章底部个人QQ名片&#xff0c;由专业技术人员远程协助&#xff01; 前言 这篇博客针对《Html网页threejs显示obj,ply三维图像实例》编写代码&#xff0c;代码整洁&#xff0…...

Windows平台下的oracle 11G-11.2.0.4补丁升级操作指南

序号 文件名称 文件说明 1 p6880880_112000_MSWIN-x86-64_OPatch 11.2.0.3.33 for DB 11.2.0.0.0 (Feb 2022) 用于升级 OPatch 2 DB_PSU_11.2.0.4.220118 (Jan 2022)_p33488457_112040_MSWIN-x86-64 主要补丁文件 注意&#xff1a;请用管理员权限运行文件内命令&#…...

MFC居中显示文字及其应用

首先获取窗口客户区矩形,然后使用DrawText输出,设置DT_CENTER 和 DT_VCENTER标志; 输出如上图;没有实现垂直居中; 最终的代码如下; void CcenterView::OnDraw(CDC* pDC) {CcenterDoc* pDoc = GetDocument();ASSERT_VALID(pDoc);if (!pDoc)return;// TODO: 在此处为…...

50-75GHz大功率六倍频源设计

摘 要 本文介绍了毫米波的特点&#xff0c;根据构成毫米波倍频器的不同器件&#xff0c;介绍了不同毫米波倍频器的实现方法&#xff0c;综述了毫米波倍频器这一领域的研究水平及其发展动态&#xff0c;重点研究频段全波导带宽倍频器的设计方法&#xff0c;从而将波段信号扩展到…...

Qt 软件调试(一) Log日志调试

终于这段时间闲下来了&#xff0c;可以系统的编写Qt软件调试的整个系列。前面零零星星的也有部分输出&#xff0c;但终究没有形成体系。借此机会&#xff0c;做一下系统的总结。慎独、精进~ 日志是有效帮助我们快速定位&#xff0c;找到程序异常点的实用方法。但是好的日志才能…...

docker network容器网络通信

Docker 网络主要有以下两个作用&#xff1a; 容器间的互联和通信以及端口映射容器IP变动时候可以通过服务名直接网络通信而不受到影响 只要是处于同一个Docker 网络下的容器就可以使用服务名直接访问&#xff0c;而无需担心重启。 docker容器网络模式 bridge网络模式&#…...

CVE-2022-4886 ingress命令注入复现与分析

安装 安装ingress-nginx wget https://raw.githubusercontent.com/kubernetes/ingress-nginx/controller-v1.8.4/deploy/static/provider/cloud/deploy.yamlk apply -f deploy.yaml 原理 nginx.ingress.kubernetes.io/rewrite-target标签会在nginx配置进行插入字符串&#…...

Oracle整体架构

4. Oracle整体架构 所谓整体架构,这里是指保证Oracle数据库系统正常工作和运行所必须的组件及其实现。从大的方面讲,这主要包括实例和数据库。在此基础上细分,实例由相关内存区域和服务进程组成,数据库包括各种相关文件,而这些相关内存区域、服务进程及相关文件又可再进一…...

webpack具体实现--未完

1、前端模块打包工具webpack webpack 是 Webpack 的核心模块&#xff0c;webpack-cli 是 Webpack 的 CLI 程序&#xff0c;用来在命令行中调用 Webpack。webpack-cli 所提供的 CLI 程序就会出现在 node_modules/.bin 目录当中&#xff0c;我们可以通过 npx 快速找到 CLI 并运行…...

【Git】修改提交信息(单次、批量)

文章目录 修改最近一次 commit 的提交信息修改某次 commit 的提交信息方法总结 修改最近一次 commit 的提交信息 git commit --amend -m "new message"修改某次 commit 的提交信息 git log --oneline 运行结果如下2f80f1b commit 4 9ee990a 第三次提交 40f2f03 comm…...

Grafana Panel组件跳转、交互实现

程序员的公众号&#xff1a;源1024&#xff0c;获取更多资料&#xff0c;无加密无套路&#xff01; 最近整理了一份大厂面试资料《史上最全大厂面试题》&#xff0c;Springboot、微服务、算法、数据结构、Zookeeper、Mybatis、Dubbo、linux、Kafka、Elasticsearch、数据库等等 …...

人工智能|机器学习——感知器算法原理与python实现

感知器算法是一种可以直接得到线性判别函数的线性分类方法&#xff0c;它是基于样本线性可分的要求下使用的。 一、线性可分与线性不可分 为了方便讨论&#xff0c;我们蒋样本增加了以为常数&#xff0c;得到增广样向量 y&#xff08;1;;;...;&#xff09;,则n个样本的集合为&a…...

【论文阅读笔记】Prompt-to-Prompt Image Editing with Cross-Attention Control

【论文阅读笔记】Prompt-to-Prompt Image Editing with Cross-Attention Control 个人理解思考基本信息摘要背景挑战方法结果 引言方法论结果讨论引用 个人理解 通过将caption的注意力图注入到目标caption注意力中影响去噪过程以一种直观和便于理解的形式通过修改交叉注意力的…...

Echarts legend图例配置项 设置位置 显示隐藏

Echarts 官网完整配置项 https://echarts.apache.org/zh/option.html#legend 配置项 legend: { }设置图例为圆形 icon: circle,//设置图例为圆形设置图例位置 top: 20%//距离顶部百分之20//y:bottom 在底部显示设置图例 宽度 高度 itemWidth: 10,//设置图例宽度 itemHeight: …...

手游刚开服就被攻击怎么办?如何防御DDoS?

开服初期是手游最脆弱的阶段&#xff0c;极易成为DDoS攻击的目标。一旦遭遇攻击&#xff0c;可能导致服务器瘫痪、玩家流失&#xff0c;甚至造成巨大经济损失。本文为开发者提供一套简洁有效的应急与防御方案&#xff0c;帮助快速应对并构建长期防护体系。 一、遭遇攻击的紧急应…...

stm32G473的flash模式是单bank还是双bank?

今天突然有人stm32G473的flash模式是单bank还是双bank&#xff1f;由于时间太久&#xff0c;我真忘记了。搜搜发现&#xff0c;还真有人和我一样。见下面的链接&#xff1a;https://shequ.stmicroelectronics.cn/forum.php?modviewthread&tid644563 根据STM32G4系列参考手…...

Qt Widget类解析与代码注释

#include "widget.h" #include "ui_widget.h"Widget::Widget(QWidget *parent): QWidget(parent), ui(new Ui::Widget) {ui->setupUi(this); }Widget::~Widget() {delete ui; }//解释这串代码&#xff0c;写上注释 当然可以&#xff01;这段代码是 Qt …...

理解 MCP 工作流:使用 Ollama 和 LangChain 构建本地 MCP 客户端

&#x1f31f; 什么是 MCP&#xff1f; 模型控制协议 (MCP) 是一种创新的协议&#xff0c;旨在无缝连接 AI 模型与应用程序。 MCP 是一个开源协议&#xff0c;它标准化了我们的 LLM 应用程序连接所需工具和数据源并与之协作的方式。 可以把它想象成你的 AI 模型 和想要使用它…...

LeetCode - 394. 字符串解码

题目 394. 字符串解码 - 力扣&#xff08;LeetCode&#xff09; 思路 使用两个栈&#xff1a;一个存储重复次数&#xff0c;一个存储字符串 遍历输入字符串&#xff1a; 数字处理&#xff1a;遇到数字时&#xff0c;累积计算重复次数左括号处理&#xff1a;保存当前状态&a…...

渲染学进阶内容——模型

最近在写模组的时候发现渲染器里面离不开模型的定义,在渲染的第二篇文章中简单的讲解了一下关于模型部分的内容,其实不管是方块还是方块实体,都离不开模型的内容 🧱 一、CubeListBuilder 功能解析 CubeListBuilder 是 Minecraft Java 版模型系统的核心构建器,用于动态创…...

WordPress插件:AI多语言写作与智能配图、免费AI模型、SEO文章生成

厌倦手动写WordPress文章&#xff1f;AI自动生成&#xff0c;效率提升10倍&#xff01; 支持多语言、自动配图、定时发布&#xff0c;让内容创作更轻松&#xff01; AI内容生成 → 不想每天写文章&#xff1f;AI一键生成高质量内容&#xff01;多语言支持 → 跨境电商必备&am…...

【python异步多线程】异步多线程爬虫代码示例

claude生成的python多线程、异步代码示例&#xff0c;模拟20个网页的爬取&#xff0c;每个网页假设要0.5-2秒完成。 代码 Python多线程爬虫教程 核心概念 多线程&#xff1a;允许程序同时执行多个任务&#xff0c;提高IO密集型任务&#xff08;如网络请求&#xff09;的效率…...

【JavaWeb】Docker项目部署

引言 之前学习了Linux操作系统的常见命令&#xff0c;在Linux上安装软件&#xff0c;以及如何在Linux上部署一个单体项目&#xff0c;大多数同学都会有相同的感受&#xff0c;那就是麻烦。 核心体现在三点&#xff1a; 命令太多了&#xff0c;记不住 软件安装包名字复杂&…...

Java数值运算常见陷阱与规避方法

整数除法中的舍入问题 问题现象 当开发者预期进行浮点除法却误用整数除法时,会出现小数部分被截断的情况。典型错误模式如下: void process(int value) {double half = value / 2; // 整数除法导致截断// 使用half变量 }此时...