「C++系列」一篇文章说透【存储类】

文章目录

  • 一、C++ 存储类
    • 1. 类的定义
    • 2. 对象的创建
    • 3. 对象在内存中的布局
    • 4. 对象的存储位置
  • 二、auto 存储类
    • 1. `auto`的基本用法
    • 2. `auto`与存储类的关系
      • 1) 自动存储类(最常见的)
      • 2) 静态存储类
      • 3) 动态存储类(通过new)
  • 三、register 存储类
    • 1. register 存储类的特点
    • 2. 案例
    • 3. 注意事项
  • 四、static 存储类
    • 1. 局部静态变量
    • 2. 全局静态变量
    • 3. 静态类成员变量
    • 4. 静态类成员函数
  • 五、extern 存储类
    • 1. 声明全局变量
    • 2. 声明函数
    • 3. extern "C"
    • 4. 注意事项
  • 六、mutable 存储类
    • 1. 基本用法
    • 2. 示例
    • 3. 注意事项
  • 七、thread_local 存储类
    • 1. 基本用法
    • 2. 注意事项
  • 八、相关链接

在这里插入图片描述

一、C++ 存储类

在C++中,类的存储方式主要涉及到类的定义、对象的创建以及这些对象在内存中的布局。C++是一种静态类型、编译型语言,支持面向对象的编程范式。下面详细解释这些概念:

1. 类的定义

类是C++中用户定义的类型(UDT),用于封装数据(称为成员变量或属性)和函数(称为成员函数或方法)。类的定义不会为对象分配任何内存,它只是描述了对象的结构。

class MyClass {
public:
    int x;
    void func() {
        // 成员函数实现
    }
};

2. 对象的创建

当你使用类来创建对象时,才会在内存中为对象分配空间。这个空间用于存储对象的成员变量。成员函数则不直接存储在对象中,而是存储在程序的代码段中,对象通过其成员函数指针(通常是通过隐式的this指针)来访问这些函数。

MyClass obj; // 创建一个MyClass类型的对象obj

3. 对象在内存中的布局

  • 成员变量:对象的成员变量(包括从基类继承的成员变量)按照它们在类中声明的顺序,在内存中连续存储。成员变量的对齐和填充(padding)可能会根据编译器和平台的不同而有所不同,以优化内存访问速度。
  • 成员函数:成员函数不直接存储在对象中,而是存储在程序的代码段(Code Segment)中。当对象调用成员函数时,该函数通过隐式的this指针来访问对象的成员变量。
  • 静态成员:静态成员变量在程序的全局数据段中分配一次内存,所有对象共享同一份静态成员变量的拷贝。静态成员函数则不直接访问任何对象的成员变量(除非通过对象或类名显式传递),因此它们没有this指针。

4. 对象的存储位置

对象的存储位置取决于其生命周期和作用域:

  • 自动存储期:在函数或代码块内声明的局部变量(包括对象)存储在栈(Stack)上,其生命周期仅限于定义它们的代码块。
  • 静态存储期:全局对象、静态局部变量以及静态成员变量存储在全局数据段(Global Data Segment)或静态数据段(Static Data Segment)中,它们在程序的整个执行期间都存在。
  • 动态存储期:通过new操作符动态分配的对象存储在堆(Heap)上,其生命周期由newdelete操作符控制。

二、auto 存储类

在C++中,auto 关键字不是用来直接声明存储类的,而是用来自动推导变量类型的。存储类(也称为存储期或生命周期)指的是变量在内存中保留的时间长度,常见的存储类有自动(automatic)、静态(static)、寄存器(register,但现代C++中很少使用,且其优化行为通常由编译器自动处理)、外部(extern)以及动态分配(通过new操作符)。

然而,当我们在C++中使用auto关键字时,我们是在告诉编译器自动根据初始化表达式的类型来推导变量的类型。这并不意味着auto变量就有特定的存储类;它的存储类取决于其声明的上下文。

1. auto的基本用法

下面是一个使用auto的简单案例,它演示了如何自动推导变量的类型,但并没有直接涉及到存储类的概念:

#include <iostream>
#include <vector>

int main() {
    // 自动推导为int类型
    auto a = 10;
    std::cout << "a is: " << a << std::endl;

    // 自动推导为std::vector<int>类型
    std::vector<int> v = {1, 2, 3, 4, 5};
    auto b = v; // 注意:这里b是v的一个拷贝,而不是引用
    std::cout << "b has " << b.size() << " elements." << std::endl;

    return 0;
}

2. auto与存储类的关系

尽管auto本身不直接声明存储类,但auto声明的变量可以根据其声明的上下文获得不同的存储类。以下是一些例子:

1) 自动存储类(最常见的)

void func() {
    auto x = 10; // x具有自动存储类,因为它是在函数内部声明的局部变量
    // ...
} // x的作用域结束,x的生命周期也结束

2) 静态存储类

static auto y = 20; // y具有静态存储类,尽管它是用auto声明的
// y的生命周期贯穿整个程序执行期间,但其作用域可能受限于声明它的块或文件

void func() {
    // 可以在这里访问y
}

注意:在全局或命名空间作用域中使用static会改变链接性(linkage),但在函数内部使用时,它主要影响生命周期和初始化时机(只初始化一次)。

3) 动态存储类(通过new)

虽然auto通常不直接与动态分配相关联,但你可以使用auto来接收new表达式的结果:

auto ptr = new int(30); // ptr是指向int的指针,具有自动存储类
// 但它指向的对象是通过new动态分配的,具有动态存储类
// 记得用delete ptr;来释放内存

在这个例子中,ptr本身是一个具有自动存储类的局部变量,但它指向的对象是通过new动态分配的,因此该对象具有动态存储类。

总结:auto用于自动推导变量类型,而变量的存储类取决于其声明的上下文(如是否在函数内部、是否使用了static关键字、是否通过new动态分配等)。

三、register 存储类

在C++中,register 存储类是一个特殊的说明符,用于向编译器建议将变量存储在CPU的寄存器中,以便快速访问。然而,需要注意的是,register 关键字仅仅是一个建议,并不保证变量一定会被存储在寄存器中。此外,从C++11开始,register 关键字被废弃,现代编译器通常会忽略它,因为它们有自己的优化机制来决定变量的存储位置。

1. register 存储类的特点

  1. 建议性register 关键字告诉编译器,程序员认为该变量应该被频繁访问,因此建议将其存储在寄存器中。但编译器可以忽略这个建议。
  2. 局部变量register 只能用于局部变量,不能用于全局变量或静态变量。
  3. 限制:使用 register 的变量不能被取地址(即不能应用一元 & 运算符),因为它可能没有内存地址。
  4. 尺寸限制register 变量的最大尺寸通常等于寄存器的大小(通常是一个词或几个词)。

2. 案例

尽管 register 关键字在现代C++编程中不再被推荐使用,但以下是一个简单的例子,展示了如果编译器支持 register 关键字时它的用法:

#include <iostream>

int main() {
    register int counter = 0; // 建议编译器将counter存储在寄存器中
    for (int i = 0; i < 1000000; i++) {
        counter++; // 假设counter被存储在寄存器中,这可能会提高循环的性能
    }
    std::cout << "Counter: " << counter << std::endl;
    return 0;
}

然而,在现代C++编译器中,即使你使用了 register 关键字,编译器也可能会忽略它,因为它有自己的优化策略来决定哪些变量应该被存储在寄存器中。

3. 注意事项

  • 废弃:由于 register 关键字在C++11中被废弃,因此在新的C++代码中应避免使用它。
  • 性能优化:如果你关心性能,并且想要优化特定变量的访问速度,最好让编译器自己处理这些优化,或者通过其他方式(如使用更高效的算法或数据结构)来提高程序性能。
  • 代码可读性:使用 register 关键字可能会降低代码的可读性,因为它引入了一个不再被现代编译器广泛支持的特性。

综上所述,虽然 register 存储类在理论上可以用于优化变量访问速度,但在现代C++编程中,它已经不再是一个有用的特性,应该被避免使用。

四、static 存储类

在C++中,static存储类是一个非常重要的特性,它用来控制变量的存储方式和可见性。以下是static存储类的详细解释:

1. 局部静态变量

static用于函数内的局部变量时,它会使该变量具有静态存储期,即变量在程序的整个执行期间都存在,但只在定义它的作用域内可见。这样的变量只初始化一次,每次函数调用时保留其最后一次使用的值。

特点

  • 存储在静态存储区。
  • 只在定义它的函数内可见。
  • 即使函数调用结束,也不会销毁。
  • 只初始化一次。

示例

#include <iostream>
using namespace std;

void countFunction() {
    static int count = 0; // 局部静态变量
    count++;
    cout << "Count: " << count << endl;
}

int main() {
    countFunction(); // 输出 1
    countFunction(); // 输出 2
    countFunction(); // 输出 3
    return 0;
}

2. 全局静态变量

在函数外部使用static声明的全局变量或函数,会限制其链接性(可见性),使其只在定义它的文件中可见。这有助于避免不同源文件之间的命名冲突。

特点

  • 存储在全局数据段。
  • 只在其定义的文件内可见。
  • 在程序的整个执行期间都存在。

示例

// file1.cpp
#include <iostream>
static int globalValue = 10;
void display() {
    std::cout << "Global Value in file1: " << globalValue << std::endl;
}

// file2.cpp
// extern int globalValue; // 如果取消注释,则会导致编译错误,因为globalValue在file2中不可见

// 假设有main函数在file2.cpp或其他地方
// 调用display函数会正常显示file1中的globalValue值

3. 静态类成员变量

在类中声明static变量时,该变量不属于任何特定的对象实例,而是类的所有实例共享的。它们必须在类外部初始化。

特点

  • 存储在静态存储区。
  • 类的所有对象共享同一份拷贝。
  • 初始化时使用作用域运算符(::)来标明它所属类。

示例

#include <iostream>
using namespace std;

class MyClass {
public:
    static int staticValue;
};

int MyClass::staticValue = 0; // 初始化

int main() {
    MyClass obj1, obj2;
    obj1.staticValue = 5;
    cout << "Static Value from obj1: " << obj1.staticValue << endl; // 输出 5
    cout << "Static Value from obj2: " << obj2.staticValue << endl; // 输出 5
    return 0;
}

4. 静态类成员函数

静态成员函数与静态数据成员一样,都是类的内部实现,属于类定义的一部分。它们可以在没有对象实例的情况下调用,并且只能访问其类的静态成员。

特点

  • 没有this指针。
  • 只能访问类的静态成员变量和静态成员函数。

示例

#include <iostream>
using namespace std;

class MyClass {
public:
    static int staticValue;
    static void displayValue() {
        cout << "Static Value: " << staticValue << endl;
    }
};

int MyClass::staticValue = 10;

int main() {
    MyClass::displayValue(); // 输出 10
    return 0;
}

五、extern 存储类

在C++中,extern关键字是一个非常重要的存储类修饰符,它主要用于声明一个全局变量或函数,这些变量或函数是在其他文件中定义的。下面详细解释extern存储类的用法和特点:

1. 声明全局变量

当我们在多个文件中使用同一个全局变量时,extern可以帮助我们实现这一目标。通过extern,我们可以在一个文件中声明该全局变量(而不是定义它,即不分配内存),然后在其他文件中使用它。这样做的好处是避免了在多个文件中重复定义同一个全局变量可能导致的编译错误。

示例

假设我们有两个文件,main.cppsupport.cpp

  • support.cpp中定义一个全局变量:
int testVar = 0; // 定义一个全局变量
  • main.cpp中,我们通过extern来声明这个全局变量,以便使用它:
extern int testVar; // 声明外部变量

int main() {
    testVar = 10; // 使用外部变量
    // ...
}

2. 声明函数

除了变量之外,extern也可以用于声明在其他文件中定义的函数。这样,我们就可以在多个文件中调用同一个函数,而不需要在每个文件中都重复函数的定义。

示例

  • support.cpp中定义一个函数:
void testFunc() {
    // 函数体
}
  • main.cpp中,我们通过extern来声明这个函数,以便调用它:
extern void testFunc(); // 声明外部函数

int main() {
    testFunc(); // 调用外部函数
    // ...
}

然而,需要注意的是,在C++中,对于函数的声明,extern通常是隐式的,即我们不需要显式地写出extern来声明一个函数是在其他文件中定义的。但在某些特殊情况下,为了强调或明确函数的外部链接性,也可以显式地使用extern

3. extern “C”

在C++中,我们还会经常看到extern "C"的用法。这是因为C++支持函数重载,而C语言不支持。当C++代码需要被C语言代码调用时,为了避免链接错误(即C++编译器对函数名进行名称修饰,而C编译器不进行),我们需要用extern "C"来告诉C++编译器按照C语言的方式来链接这些函数。

示例

extern "C" void testFunc() {
    // 函数体
}

或者,在头文件中声明时:

#ifdef __cplusplus
extern "C" {
#endif

void testFunc();

#ifdef __cplusplus
}
#endif

4. 注意事项

  • extern只是声明,不是定义。它告诉编译器变量或函数的类型,但不会分配内存。
  • extern声明的变量或函数必须在某个文件中被定义,否则在链接阶段会报错。
  • extern只能用于全局变量和函数,不能用于函数内部的局部变量。
  • 在C++中,对于函数的声明,extern通常是隐式的,但对于全局变量或需要明确指出外部链接性的函数,extern是必需的。

六、mutable 存储类

在C++中,mutable关键字是一个特殊的存储类修饰符,它用于类的成员变量上,以允许这个成员变量即使在常量成员函数(即被const修饰的成员函数)中也能被修改。这个特性在需要缓存计算结果、跟踪对象状态变化等场景中非常有用,特别是当这些变化不应该影响对象的逻辑常量性时。

1. 基本用法

当你将mutable关键字应用于类的成员变量时,这个成员变量即使在常量成员函数中也可以被修改。这意呀着,常量成员函数(即被声明为const的成员函数)可以修改这个mutable成员变量的值,而不会违反const成员函数不应修改任何成员变量的常规规则。

2. 示例

#include <iostream>

class MyClass {
private:
    mutable int cache; // 使用mutable修饰,允许在const成员函数中被修改
    int value;

public:
    MyClass(int v) : value(v), cache(-1) {} // 初始化value,cache初始化为-1表示未计算

    // 常量成员函数,但可以修改mutable成员变量cache
    int getValue() const {
        if (cache == -1) { // 如果cache未被计算
            cache = computeValue(); // 计算并存储结果
        }
        return cache;}
    

    // 非const成员函数,可以修改所有成员变量
    void setValue(int v) {
        value = v;
        cache = -1; // 重置cache,因为value的改变可能影响计算结果
    }

private:
    // 假设这是一个耗时的计算过程
    int computeValue() const {
        // ... 进行计算 ...
        return value * 2; // 仅为示例
    }
};

int main() {
    MyClass obj(5);
    std::cout << "Value: " << obj.getValue() << std::endl; // 输出:Value: 10
    obj.setValue(10);
    std::cout << "New Value: " << obj.getValue() << std::endl; // 输出:New Value: 20
    return 0;
}

3. 注意事项

  • mutable只能用于类的成员变量上。
  • 使用mutable要谨慎,因为它可能会让代码的阅读者感到困惑,特别是当常量成员函数实际上修改了某些状态时。因此,建议只在确实需要时才使用mutable,并且确保在文档中清楚地说明这一点。
  • mutable成员变量通常用于缓存计算结果、状态跟踪等场景,这些场景中的变化不会影响对象的逻辑常量性。
  • mutable成员变量不会改变常量成员函数的const性质,即常量成员函数仍然不能修改类的非mutable成员变量。

七、thread_local 存储类

在C++11及以后的版本中,thread_local关键字被引入作为一个存储类修饰符,用于声明线程局部存储(Thread-Local Storage, TLS)的变量。这意味着每个线程都有该变量的一个独立实例,线程之间对这些变量的修改是互不影响的。

1. 基本用法

当你在变量声明前加上thread_local关键字时,这个变量就变成了线程局部的。每个线程对这个变量的访问都指向它自己的独立实例。

#include <iostream>
#include <thread>

thread_local int tls_var = 0; // 线程局部变量

void increment() {
    tls_var++; // 每个线程都会增加它自己的tls_var实例
    std::cout << "Thread " << std::this_thread::get_id() << " sees tls_var as " << tls_var << std::endl;
}

int main() {
    std::thread t1(increment);
    std::thread t2(increment);

    increment(); // 主线程也会执行

    t1.join();
    t2.join();

    return 0;
}

在这个例子中,每个线程(包括主线程)都会打印出它自己的tls_var值,这些值在每次调用increment函数时都会递增,但每个线程看到的都是它自己的独立副本。

2. 注意事项

  • thread_local变量在其所属线程开始时被构造,在线程结束时被销毁。这意味着你不能在全局作用域中直接初始化一个需要构造函数和析构函数的thread_local变量,因为全局变量的构造和析构发生在程序开始和结束时,而这时线程可能还没有开始或已经结束。
  • thread_local变量不会跨线程共享,这意呀着每个线程对其的修改都不会影响到其他线程。
  • 在某些平台上,thread_local变量的实现可能依赖于动态内存分配,这可能会引入额外的性能开销。此外,如果线程数量非常多,可能会消耗大量的内存。
  • 在使用thread_local时,要特别注意内存泄漏和异常安全问题。如果thread_local变量在析构时抛出异常,并且这个异常没有被捕获,那么程序可能会以未定义的方式终止。
  • 并不是所有的C++实现都支持thread_local,但它被C++11标准所要求,因此大多数现代编译器都支持它。

八、相关链接

  1. Visual Studio Code下载地址
  2. Sublime Text下载地址
  3. 「C++系列」C++简介、应用领域
  4. 「C++系列」C++ 基本语法
  5. 「C++系列」C++ 数据类型
  6. 「C++系列」C++ 变量类型
  7. 「C++系列」C++ 变量作用域
  8. 「C++系列」C++ 常量知识点-细致讲解
  9. 「C++系列」C++ 修饰符类型

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/793885.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

SSRF漏洞深入利用与防御方案绕过技巧

文章目录 前言SSRF基础利用1.1 http://内网资源访问1.2 file:///读取内网文件1.3 dict://探测内网端口 SSRF进阶利用2.1 Gopher协议Post请求2.2 Gopher协议文件上传2.3 GopherRedis->RCE2.4 JavaWeb中的适用性&#xff1f; SSRF防御绕过3.1 Url黑名单检测的绕过3.2 Url白名单…

【PHP安装内置扩展】

PHP安装内置扩展 1、首先查看php源码以及查询是否有需要的扩展;本次以zlib扩展为例子 2、进入需要安装的扩展目录,执行命令 cd zlib 执行 make clean 清掉之前的安装的残留文件; 不需要的话直接略过,新安装也略过3、运行phpize,执行/usr/local/php/bin/phpize 注意这个路径一…

【BES2500x系列 -- RTX5操作系统】深入探索CMSIS-RTOS RTX -- 配置篇 -- 初识GPIO --(六)

&#x1f48c; 所属专栏&#xff1a;【BES2500x系列】 &#x1f600; 作  者&#xff1a;我是夜阑的狗&#x1f436; &#x1f680; 个人简介&#xff1a;一个正在努力学技术的CV工程师&#xff0c;专注基础和实战分享 &#xff0c;欢迎咨询&#xff01; &#x1f49…

子任务:IT运维的精细化管理之道

在当今的企业运营中&#xff0c;信息技术已成为支撑业务发展的核心力量。根据Gartner的报告&#xff0c;IT服务管理&#xff08;ITSM&#xff09;的有效实施可以显著提升企业的运营效率&#xff0c;降低成本高达15%&#xff0c;同时提高服务交付速度和质量。随着业务的复杂性和…

7个外贸网站模板

Nebula独立站wordpress主题 Nebula奈卜尤拉wordpress主题模板&#xff0c;适合搭建外贸独立站使用的wordpress主题。 https://www.jianzhanpress.com/?p7084 Starling师大林WordPress独立站模板 蓝色橙色风格的WordPress独立站模板&#xff0c;适合做对外贸易的外贸公司搭建…

pytorch 是如何调用 cusolver API 的调用

0&#xff0c;环境 ubuntu 22.04 pytorch 2.3.1 x86 RTX 3080 cuda 12.2 1, 示例代码 以potrs为例&#xff1b; hello_cholesk.py """ hello_cholesky.py step1, Cholesky decompose; step2, inverse A; step3, Cholesky again; python3 hello_cholesky.py -…

Hi3861 OpenHarmony嵌入式应用入门--华为 IoTDA 设备接入

华为云物联网平台&#xff08;IoT 设备接入云服务&#xff09;提供海量设备的接入和管理能力&#xff0c;可以将自己的 IoT 设备 联接到华为云&#xff0c;支撑设备数据采集上云和云端下发命令给设备进行远程控制&#xff0c;配合华为云物联网平台的服 务实现设备与设备之间的控…

【区块链农场】:农场游戏+游戏

我的酒坊是一款非常受玩家欢迎的经营手游,游戏中你需要合理经营一家酒厂,将其做大做强。通过制定合理的战略,例如新建厂房,并采用传统工艺制作,针对不同的人群研制多重口味。

配置sublime的中的C++编译器(.sublime-build),实现C++20在sublime中的使用,小白教程

一&#xff0c;前期准备 首先我们需要准备一下 C 环境&#xff0c;当然如果你觉得你当前的C环境配置好了&#xff0c;并且C的版本也能完成您日常的使用需求&#xff0c;您可以使用下面两条命令对C的版本进行查询 g -vg --version通过返回的版本简单的判断是否能解决您的需求&…

[Godot3.3.3] - 过渡动画

过渡动画 ScreenTransitionAnimation 项目结构 添加场景&#xff0c;根节点为 CanvasLayer2D 并重命名为 ScreenTransition: 添加子节点 ColorRect 和 AnimationPlayer&#xff0c;在 ColorRect 中将颜色(Color)设置为黑色&#xff1a; 找到 Material&#xff0c;新建 Shader…

【Element-UI 表格表头、内容合并单元格】

一、实现效果&#xff1a; &#x1f970; 表头合并行、合并列 &#x1f970; &#x1f970; 表格内容行、合并列 &#x1f970; thead和tbody分别有单独的合并方法 二、关键代码&#xff1a; <el-table size"mini" class"table-th-F4F6FB" align&qu…

初识c++(类与对象——上)

一、类的定义 1、类定义格式 • class为定义类的关键字&#xff0c;Stack为类的名字&#xff0c;{}中为类的主体&#xff0c;注意类定义结束时后面分号不能省 略。类体中内容称为类的成员&#xff1a;类中的变量称为类的属性或成员变量; 类中的函数称为类的方法或 者成员函…

【C++初阶】类和对象(上)

【C初阶】类和对象&#xff08;上&#xff09; &#x1f955;个人主页&#xff1a;开敲&#x1f349; &#x1f525;所属专栏&#xff1a;C&#x1f96d; &#x1f33c;文章目录&#x1f33c; 1. 面向过程和面向对象初步认识 2. 类的引入 3. 类的定义 4. 类的访问限定符及封…

python 实验八 数据分析与展示

一、实验目的 掌握掌握matplotlib库中pyplot模块的使用。 二、实验环境 Window10&#xff08;x64&#xff09;&#xff0c;Python 3.8&#xff08;x64&#xff09;&#xff0c;PyCharm Community Edition 2020.3.2&#xff08;x64&#xff09; 三、实验内容 现有列表hight…

jmeter分布式(四)

一、gui jmeter的gui主要用来调试脚本 1、先gui创建脚本 先做一个脚本 演示&#xff1a;如何做混合场景的脚本&#xff1f; 用211的业务比例 ①启动数据库服务 数据库服务&#xff1a;包括mysql、redis mysql端口默认3306 netstat -lntp | grep 3306处于监听状态&#xf…

[迫真保姆级教程]在Windows上编译可用的Tesseract OCR in C++ 并部署在Visual Studio与Qt6上

目录 前言 阅前提示 导言 使用基于vcpkg的&#xff0c;于msvc19编译器编译的Tessereact OCR动态库 使用vcpkg辅助我们的编译 正文 使用msys2环境下的&#xff0c;使用mingw64编译器编译的Tessereact OCR动态库 什么是msys2 安装前&#xff0c;我们也许。。。 [Option]…

python作业二

# 二进制转化为十进制 num input("num:")def binaryToDecimal(binaryString):he 0length len(binaryString)for i in range(length):he int(binaryString[i]) * 2 ** (length - i - 1)return heprint(binaryToDecimal(num))代码运行如下&#xff1a; import math…

基于YOLOV8的数粒机-农业应用辣椒种子计数计重双标质量解决方案

一:辣椒种子行业背景调查 中国辣椒年产量稳居世界第一,食辣人口超5亿。中国辣椒全球闻名,小辣椒长成大产业,带动全球食品行业腾飞。 在中国,“辣”是不少地方餐桌上的一大特色。从四川的麻辣火锅到湖南的剁椒鱼头再到陕西的油泼辣子面,由南到北,总有食客对辣有着独一份偏…

【RHCE】系统服务综合实验

一、实验内容 现有主机 node01 和 node02&#xff0c;完成如下需求&#xff1a; 1、在 node01 主机上提供 DNS 和 WEB 服务 2、dns 服务提供本实验所有主机名解析 3、web服务提供 www.rhce.com 虚拟主机 4、该虚拟主机的documentroot目录在 /nfs/rhce 目录 5、该目录由 node02…

牛顿力学和拉格朗日力学求解atwood machine问题对比

一个半径为 R R R、转动惯量为 I I I 的圆盘。绳子与圆盘无滑动&#xff0c;质量 m 2 m_2 m2​ 的物体在重力 g g g 作用下下坠&#xff0c;带动质量 m 1 m_1 m1​ 的物体上升。求 m 1 m_1 m1​和 m 2 m_2 m2​ 的加速度 a a a。 牛顿力学方法 对质量 m 1 m_1 m1​ 和 …