保存时间:2026/4/1 00:22:08
| 线路 | 起点站 | 首站发车时间 | 终点站 | 末站发车时间 | 最早开通日期 | 识别色 |
|---|---|---|---|---|---|---|
| BRT 快 1 线 | 第一码头枢纽站 | 05:45-22:15 | 厦门北站 | 06:10-23:30 | 2008 年 8 月 31 日 | 绿色 |
| BRT 快 2 线 | 第一码头枢纽站 | 06:10-21:15 | 同安枢纽站 | 06:10-21:15 | 2008 年 8 月 31 日 | 黄色 |
| BRT 快 3 线 | 第一码头枢纽站 | 06:10-23:00 | 前埔枢纽站 | 06:10-23:00 | 2008 年 8 月 31 日 | 红色 |
| BRT 快 5 线 | 前埔枢纽站 | 06:10-21:15 | 同安枢纽站 | 06:10-21:15 | 2015 年 8 月 1 日 | 蓝色 |
| BRT 快 6 线 | 前埔枢纽站 | 06:10-21:15 | 厦门北站 | 06:10-21:15 | 2016 年 1 月 31 日 | 橙色 |
| BRT 快 7 线 | 同安枢纽站 | 06:10-21:15 | 厦门北站 | 06:10-21:15 | 2023 年 1 月 16 日 | 紫色 |
| BRT 快 8 线(高峰线路) | 第一码头枢纽站 | 07:10-09:16,17:10-19:06 | 高崎机场枢纽站 | 07:00-09:00,... |
| 区域 | 价格(元 / 平方米) |
|---|---|
| 思明 | 71150 |
| 湖里 | 65760 |
| 集美 | 38242 |
| 海沧 | 30032 |
| 翔安 | 26500 |
| 同安 | 24327 |
| 厦门周边 | 14299 |
sudo apt-get install gpartedsudo gparted即可启动该工具。需要注意的是,对已挂载的分区进行操作(如删除、变更大小等)时,必须先卸载该分区。运交华盖欲何求,未敢翻身已碰头。
破帽遮颜过闹市,漏船载酒泛中流。
横眉冷对千夫指,俯首甘为孺子牛。
躲进小楼成一统,管他冬夏与春秋。
sudo apt update and sudo apt upgrade.sudo apt install build-essential cmake libboost-all-dev liblua5.2-dev libsdl2-dev libsdl2-image-dev libsdl2-mixer-dev libsdl2-ttf-dev zlib1g-devgit clone https://github.com/vcmi/vcmi.gitcd vcmigit checkout tags/v1.2mkdir build && cd buildcmake..make -j$(nproc)sudo make installgit clone https://github.com/vcmi/vcmi.git,然后进入项目目录,使用CMake构建项目,例如在创建的build目录中执行cmake..和make命令。构建完成后,运行./vcmiclient即可启动游戏,但需要注意该项目不是独立程序,需要拥有《英雄无敌3》的原始游戏文件才能正常运行。int num = 10;。if (num > 5) {
// 执行的代码
} else {
// 其他情况执行的代码
}
int add(int a, int b) {
return a + b;
}
int result = add(3, 4);
class Rectangle {
public:
int width;
int height;
int area() {
return width * height;
}
};
Rectangle rect;
rect.width = 5;
rect.height = 3;
int area = rect.area();
class Shape {
public:
virtual void draw() = 0;
};
class Circle : public Shape {
public:
void draw() override {
// 绘制圆形的代码
}
};
class Square : public Shape {
public:
void draw() override {
// 绘制正方形的代码
}
};
template <typename T>
T max(T a, T b) {
return a > b? a : b;
}
int a = 5, b = 7;
int result1 = max(a, b);
double c = 3.5, d = 4.2;
double result2 = max(c, d);
template <typename T>
class Stack {
private:
T* data;
int top;
int capacity;
public:
Stack() : top(-1), capacity(10) {
data = new T[capacity];
}
void push(T item) {
// 入栈操作
}
T pop() {
// 出栈操作
return T();
}
bool isEmpty() {
return top == -1;
}
};
Stack<int> intStack;
Stack<double> doubleStack;
std::vector<int> vec;
vec.push_back(1);
vec.push_back(2);
vec.push_back(3);
for (int i : vec) {
std::cout << i << " ";
}
int arr[] = { 5, 3, 8, 2, 7 };
std::vector<int> vec(arr, arr + 5);
std::sort(vec.begin(), vec.end());
for (int i : vec) {
std::cout << i << " ";
}
git clone https://github.com/google/googletest.git。cd googletest && mkdir build && cd build。cmake..。make && sudo make install。apt - get install libgtest - dev(安装后可能还需要手动构建库文件)。gtest/gtest.h。TEST开头,后面跟着测试套件名(Test Suite Name)和测试用例名(Test Case Name),格式为TEST(TestSuiteName, TestCaseName)。例如:#include "gtest/gtest.h"
// 测试一个加法函数
int add(int a, int b) {
return a + b;
}
TEST(AddFunctionTest, BasicAddition) {
int result = add(3, 4);
EXPECT_EQ(result, 7);
}
EXPECT_EQ:用于检查两个值是否相等。例如,EXPECT_EQ(x, y)会检查x和y是否相等,如果不相等则测试失败。EXPECT_NE:检查两个值是否不相等。EXPECT_TRUE和EXPECT_FALSE:分别用于检查一个表达式是否为真或假。EXPECT_LE(小于等于)、EXPECT_LT(小于)、EXPECT_GE(大于等于)和EXPECT_GT(大于):用于比较大小关系。main函数来运行测试。可以使用Google Test提供的RUN_ALL_TESTS宏来运行所有的测试用例。例如:#include "gtest/gtest.h"
// 其他测试用例...
int main(int argc, char** argv) {
::testing::InitGoogleTest(&argc, argv);
return RUN_ALL_TESTS();
}
g++ -lgtest -lgtest_main test_file.cpp -o test_program。./test_program,就会执行所有的测试用例,并输出测试结果,包括每个测试用例是否通过、失败的原因(如果有)等信息。EXPECT_CALL宏来设置这些期望。例如:// 假设我们有一个接口类
class MyInterface {
public:
virtual int myFunction(int arg) = 0;
};
// 测试函数
TEST(MyTest, MockFunctionCall) {
// 创建模拟对象
MockMyInterface mockObj;
// 定义期望行为
EXPECT_CALL(mockObj, myFunction(5)).WillOnce(Return(10));
// 在这里使用模拟对象进行测试,当调用myFunction(5)时,将返回10
}
Return操作。还可以设置函数调用时抛出异常、按顺序调用多个函数等多种行为。例如,使用Throw可以指定函数调用时抛出一个异常:EXPECT_CALL(mockObj, myFunction(3)).WillOnce(Throw(std::runtime_error("Test error")));
_是一个通配符,表示匹配任何参数值。EXPECT_CALL(mockObj, myFunction(_)).WillOnce(Return(7));
MOCK_METHOD宏来创建模拟类,这个宏会自动生成模拟函数的定义。例如:class MyAbstractClass {
public:
virtual ~MyAbstractClass() {}
virtual bool someFunction(const std::string& input) = 0;
};
class MockMyAbstractClass : public MyAbstractClass {
public:
MOCK_METHOD(bool, someFunction, (const std::string&), (override));
};
TEST(MyTest, TestWithMock) {
MockMyAbstractClass mockObj;
EXPECT_CALL(mockObj, someFunction("test")).WillOnce(Return(true));
MyClassUnderTest testedObj(mockObj);
// 调用被测试对象的函数,它会使用模拟对象
bool result = testedObj.doSomething();
EXPECT_TRUE(result);
}
Shape,它有一个纯虚函数area()用于计算形状的面积。class Shape {
public:
virtual double area() = 0;
};
MockShape,使用MOCK_METHOD宏来定义模拟的area函数。class MockShape : public Shape {
public:
MOCK_METHOD(double, area, (), (override));
};
area函数的返回值等行为,以测试依赖于Shape接口的其他代码。Calculator,它有一个加法函数add。class Calculator {
public:
int add(int a, int b) {
return a + b;
}
};
Calculator类中add函数对应的模拟函数,并设置期望行为。不过这种方式相对来说不太符合常规的面向对象设计原则和gmock的最佳实践,因为它绕过了接口抽象的概念。Config.json 文件中与英雄能力相关的部分是如何组织的。通常,英雄的能力可能会以特定的键值对形式存储,例如:{
"heroes": {
"strength": 10,
"intelligence": 15,
"dexterity": 8
}
}
Config.json 文件。这个部分可能会使用编程语言提供的 JSON 解析库来将文件内容转换为程序可以处理的数据结构。例如,在 Python 中可以使用 json 模块:import json
with open('Config.json') as file:
config = json.load(file)
Hero 类,可能会有以下方式修改能力值:hero = config["heroes"]
hero["strength"] += 5 # 增加力量值
Config.json 文件。同样,可以使用 JSON 解析库来实现这个功能。例如,在 Python 中:with open('Config.json', 'w') as file:
json.dump(config, file)
sudo raspi-config,进入配置界面后选择 “2 Network Options”,再选择 “N2 Wi-fi” 进行与上述类似的配置。git clone https://github.com/oblique/create_ap.git 下载项目源码,进入 create_ap 目录后执行 sudo make install 安装 create_ap.sudo apt-get install util-linux procps hostapd iproute2 iw haveged dnsmasq 安装软件运行依赖的库.sudo create_ap -n wlan0 zsc 123456789 创建 AP 热点,其中 wlan0 是无线网卡接口,zsc 是 WIFI 名称,123456789 是密码,创建成功后,其他设备可搜索到该热点并连接来访问树莓派上的资源./etc/rc.local 文件中添加 create_ap -n wlan0 zsc 123456789./etc/network/interfaces 文件,添加如下内容 :auto lo
iface lo inet loopback
iface eth0 inet dhcp
auto wlan0
allow-hotplug wlan0
iface wlan0 inet static
address 192.168.1.2
netmask 255.255.255.0
gateway 192.168.1.1
dns-nameservers x.x.x.x
address 是树莓派的静态 IP 地址,netmask 是子网掩码,gateway 是默认网关,dns-nameservers 是 DNS 服务器地址,可根据实际网络环境进行修改 。2. 编辑 /etc/wpa_supplicant/wpa_supplicant.conf 文件,添加如下内容 :ctrl_interface=/var/run/wpa_supplicant
ctrl_interface_group=0
ap_scan=2
network={
ssid="wifi名称"
proto=wpa2
key_mgmt=wpa-psk
pairwise=tkip
group=tkip
psk="wifi密码"
}
sudo /etc/init.d/networking restart 或 sudo service networking restart./etc/wpa_supplicant/wpa_supplicant.conf 文件来配置 WIFI,在该文件中添加网络详细信息,如 ctrl_interface=/var/run/wpa_supplicant、ctrl_interface_group=0、ap_scan=2 以及 network={ssid="wifi名称",proto=wpa2,key_mgmt=wpa-psk,pairwise=tkip,group=tkip,psk="wifi密码"} 等内容. 还可通过修改 /etc/network/interfaces 文件来配置网络接口等信息,如设置是否使用 DHCP、静态 IP 地址、网关、DNS 服务器地址等./boot/wpa_supplicant.conf 文件配置 WIFI 的 SSID 和密码,树莓派启动后会自行读取该配置文件连接 WIFI 设备.sudo nano /etc/modules,在文件末尾添加spi-bcm2835,以启用SPI模块.sudo nano /etc/modprobe.d/fbtft.conf,添加options fbtft_device name=adafruit18_green gpios=reset:27,dc:25,cs:8,led:24 speed=40000000 bgr=1 fps=60 custom=1 height=128 width=128 rotate=180,用于配置fbtft驱动的相关参数.sudo apt-get install cmake git安装必要的软件包,再使用git clone https://github.com/tasanakorn/rpi-fbcp下载fbcp工具源码,进入源码目录进行编译安装,最后将其设置为开机自启./boot/config.txt文件,添加hdmi_force_hotplug=1、hdmi_cvt=128 128 60 1000、hdmi_group=2、hdmi_mode=1、hdmi_mode=87、display_rotate=1等参数,以设置用户界面的显示尺寸和旋转角度等./boot/config.txt 文件,添加或修改与SPI显示屏相关的配置参数,如 dtparam=spi=on 以启用SPI接口,还可能需设置显示屏的分辨率、色彩深度、旋转角度等参数,如 hdmi_cvt=128 128 60 1 0 0 0 表示设置分辨率为128x128,刷新率60Hz.sudo raspi-config,进入配置界面,选择 “Interfacing Options” -> “SPI”,将SPI接口设置为启用状态,保存并重启树莓派.wlan0 接口,可以使用以下命令:sudo ifconfig wlan0 down,此命令通过 ifconfig 工具将 wlan0 接口关闭,使其停止网络通信等活动。执行该命令需 root 权限,故使用 sudo。sudo ip link set wlan0 down,这里的 ip 命令同样可用于网络配置,link set 子命令用于设置网络接口属性,down 表示关闭接口,同样需 root 权限来执行。sudo apt-get update和sudo apt-get install hostapd dnsmasq,安装 hostapd 和 dnsmasq 软件包。/etc/hostapd/hostapd.conf文件,添加以下内容:interface=wlan0
driver=nl80211
ssid=Your_WIFI_SSID
hw_mode=g
channel=6
macaddr_acl=0
auth_algs=1
ignore_broadcast_ssid=0
wpa=2
wpa_passphrase=Your_WIFI_Password
wpa_key_mgmt=WPA-PSK
wpa_pairwise=TKIP
rsn_pairwise=CCMP
Your_WIFI_SSID和Your_WIFI_Password替换为自定义的 WIFI 名称和密码 。/etc/dnsmasq.conf文件,添加以下内容:interface=wlan0
dhcp-range=192.168.4.2,192.168.4.20,255.255.255.0,24h
sudo systemctl unmask hostapd,sudo systemctl enable hostapd,sudo systemctl start hostapd以及sudo systemctl start dnsmasq,启动 hostapd 和 dnsmasq 服务。sudo wget -q https://git.io/voEUQ -O /tmp/raspap && bash /tmp/raspap
http://raspberrypi.local:80或http://<树莓派的IP地址>:80,进入 RaspAP 的配置页面,在该页面可设置 WIFI 名称、密码、加密方式等参数。fastboot应用程序是能够刷新设备的引导程序的。fastboot是一种用于在Android设备中启动引导程序的工具。在Ubuntu等Linux系统上,当Android设备通过USB连接到电脑且处于特定模式(如fastboot模式)时,使用fastboot命令可以执行各种操作,包括刷写固件、备份数据、解锁或锁定引导程序等。fastboot flash命令来刷写特定的分区,如fastboot flash boot boot.img可以刷写设备的引导分区。不过,使用fastboot操作具有一定风险,如果操作不当可能会导致设备无法正常启动或使用,甚至可能会损坏设备。在进行相关操作之前,一定要做好数据备份,并谨慎按照正确的操作步骤进行。.desktop文件中设置程序环境变量,步骤如下:.desktop文件,一般在/usr/share/applications/或者~/.local/share/applications/目录下。可以通过文本编辑器(如gedit)打开它。Exec行设置环境变量。假设要运行一个名为my_program的程序,并且要设置一个环境变量MY_VARIABLE=value,原始的Exec行可能是Exec=my_program。修改为Exec=env MY_VARIABLE=value my_program。这样,当通过这个.desktop文件启动程序时,就会设置该环境变量。.desktop文件中设置多个环境变量,可以按照以下步骤进行:.desktop文件。它通常位于/usr/share/applications/或~/.local/share/applications/目录中。可以使用文本编辑器(如gedit)打开。Exec行设置环境变量。假设要运行一个程序my_program,并且要设置两个环境变量VAR1=value1和VAR2=value2,原始Exec行如果是Exec = my_program,修改后的Exec行应该是Exec = env VAR1=value1 VAR2=value2 my_program。.desktop文件启动程序时,就会为程序设置多个指定的环境变量。不过这些环境变量仅在通过这个.desktop文件启动程序时起作用。pkexec出现“Display environment”未设置的错误时,这是因为pkexec在执行命令时需要知道图形显示相关的环境变量,通常是DISPLAY变量。pkexec命令前先设置DISPLAY环境变量。在终端中,可以使用以下命令:export DISPLAY=:0(这里假设你的图形显示环境变量是:0,一般情况下是这个值,但可能因你的系统配置而不同)。pkexec相关的命令,例如pkexec my_command。polkit的配置没有正确处理环境变量。polkit用于管理系统的权限,包括pkexec的执行。/etc/polkit - 1/localauthority.conf.d/目录下的配置文件(如果有的话),看是否有对DISPLAY环境变量设置的相关限制或者错误配置。不过修改这些配置文件需要谨慎,因为不正确的修改可能会导致系统权限管理出现问题。pkexec权限运行时,可能对DISPLAY环境变量有特殊的要求。可以查看应用程序的文档或者社区论坛,了解是否有针对这种情况的特定解决方法。os模块的environ属性来设置和获取环境变量。os.environ是一个类似于字典的对象,包含了当前环境中的所有环境变量。MY_VARIABLE,值为my_value的环境变量,可以使用以下代码:import os
os.environ["MY_VARIABLE"] = "my_value"
ANOTHER_VARIABLE,值为another_value:os.environ["ANOTHER_VARIABLE"] = "another_value"
os.environ设置的环境变量仅在当前Python进程及其子进程中有效。如果希望在整个系统范围内设置环境变量(这种情况较少,且通常需要管理员权限),这种方法是不行的。subprocess模块来调用外部命令时,可以将自定义的环境变量传递给子进程。ls)时设置一个环境变量MY_VARIABLE,可以这样写:import subprocess
my_env = os.environ.copy()
my_env["MY_VARIABLE"] = "my_value"
subprocess.call(["ls"], env = my_env)
os.environ.copy(),然后在这个复制的环境变量字典中添加或修改了想要的环境变量。最后,在调用subprocess.call()或者其他subprocess相关的函数(如subprocess.Popen())时,将这个自定义的环境变量字典通过env参数传递进去。/etc/environment文件来设置全局环境变量。使用文本编辑器打开/etc/environment,添加一行DISPLAY=:0(假设你的显示环境变量是:0,你可能需要根据实际情况修改这个值)。这样,每次系统启动时,这个环境变量就会被设置。/etc/profile或/etc/bash.bashrc(对于基于Debian和Ubuntu的系统)等系统级的启动脚本文件中添加设置DISPLAY环境变量的代码。例如,在/etc/profile中添加export DISPLAY=:0。不过这种方法可能只对通过bash登录的用户有效。.bashrc或.bash_profile文件中设置环境变量。打开~/.bashrc(如果使用的是bash shell),添加export DISPLAY=:0。这样,每次该用户登录时,这个环境变量就会被设置。这种方法只影响特定用户,比较适合个人定制环境变量。Xorg相关的配置文件中设置显示环境变量。不过这种方法比较复杂,并且因不同的Linux发行版和Xorg版本而异。一般不建议初学者使用这种方式。pkexec等工具应该能够获取到设置好的DISPLAY环境变量。不过要注意,修改系统级配置文件可能会影响系统的稳定性,在修改之前最好备份相关文件。.desktop文件通常是由桌面环境(如GNOME、KDE等)来处理的。这些桌面环境有相应的文件管理器和启动器组件,它们负责解析.desktop文件的内容并根据其中的指令来启动应用程序。例如,GNOME桌面环境中的nautilus文件管理器在检测到用户双击.desktop文件时,会读取文件中的Exec行,来执行对应的应用程序。.desktop文件的权限设置不正确,可能导致无法运行。例如,文件所有者没有执行权限。可以通过在终端中使用chmod命令来修改权限,如chmod +x filename.desktop,给文件所有者添加执行权限。.desktop文件本身的内容可能有错误。例如,Exec行指定的程序路径不正确,或者缺少必要的参数等。可以通过查看.desktop文件(使用文本编辑器)来检查内容是否正确。.desktop文件。可以尝试重新启动桌面环境(在终端中使用gnome - session - quit然后重新登录,适用于GNOME桌面环境)来解决这个问题。echo $DISPLAY命令来查看当前用户的显示环境变量值。如果显示为:0、:0.0或类似的值,这通常表示主显示器。但如果这个命令没有返回任何内容或者返回一个错误,可能表示没有正确设置显示环境变量。DISPLAY环境变量相关的编号。/var/log/Xorg.0.log(如果是第一个Xorg会话)。在日志文件中,可能会找到与显示器连接和设备编号相关的内容,这些内容可以帮助你确定正确的DISPLAY环境变量值。不过,分析日志文件需要一些经验,因为其中包含大量的技术信息。DISPLAY值,如:0(最常见的主显示器值)、:0.0、:1(可能用于第二个显示器或虚拟显示器)等。不过,这种方法可能需要多次尝试,并且在某些情况下可能会导致系统出现不稳定或其他问题。sudo apt - get update(用于更新软件源列表),然后输入sudo apt - get install gksu来安装gksu。gksu gedit(在终端中)这样的命令来运行,而不是用pkexec。不过,使用gksu授予程序root权限也应该谨慎,因为这可能会带来安全隐患。apt - get找不到gksu软件包,可能是因为这个软件包在官方源中的名称有所变化,或者已经被弃用。gksu。在添加软件源后,记得运行sudo apt - get update来更新软件源列表。gksu可能难以安装,考虑使用其他替代工具来实现类似的功能。例如,可以使用gksudo(如果能安装的话),它的功能和gksu比较相似,也是用于在图形界面环境下以root权限运行程序。pkexec来解决显示连接的问题,而不是寻找替代工具。如确保DISPLAY环境变量正确设置,检查相关的polkit配置文件等。file_str = "这是一个错误的文件对象示例"
file_str.read() # 这里会报错,因为file_str是字符串,不是真正的文件对象
open函数来打开文件,创建真正的文件对象,比如:file_obj = open("your_file.txt", "r")
content = file_obj.read()
file_obj.close()
def process_file(file_obj):
# 假设这里对文件对象进行一些处理
content = file_obj.read()
print(content)
file_str = "又是一个错误的示例"
process_file(file_str) # 会报错,因为传递的是字符串而非文件对象
open函数正确打开的文件对象,而不是把字符串错当成文件对象来进行与文件相关的操作。.desktop文件主要是由桌面环境中的组件来执行的。GNOME Shell和nautilus(文件管理器)协同处理。当你双击.desktop文件时,nautilus会检测到这个操作,它会读取.desktop文件中的信息,特别是Exec字段(这个字段包含了要执行的程序的命令行),然后GNOME Shell会根据这些信息启动对应的应用程序。Plasma Workspace和Dolphin(文件管理器)来处理.desktop文件,其原理和GNOME类似,也是通过读取文件内容来启动相应程序。cat命令查看其内容。例如,如果有一个名为myapp.desktop的文件位于/usr/share/applications/目录下,可以使用cat /usr/share/applications/myapp.desktop来查看其中的内容,包括程序名称、图标、启动命令等信息。Exec行的内容并在命令行运行。假设.desktop文件的Exec行内容是/usr/bin/myapp,那么可以在命令行直接运行/usr/bin/myapp来启动对应的应用程序。不过,有些.desktop文件的Exec行可能包含参数或者环境变量设置,需要一并考虑。[Desktop Entry]
Name=My Application
Exec=/usr/bin/myapp - arg1 - arg2
Icon=/usr/share/icons/myapp_icon.png
Type=Application
/usr/bin/myapp - arg1 - arg2即可。如果Exec行还包含环境变量设置,比如Exec=env VAR1=value1 /usr/bin/myapp - arg1 - arg2,可以先设置环境变量(如export VAR1=value1),然后再运行/usr/bin/myapp - arg1 - arg2。Exec字段,这个字段包含了启动应用程序的命令行。然后,GNOME Shell会根据这个命令行来启动对应的应用程序,包括解析命令行中的参数、设置环境变量等操作。myapp.desktop,使用命令ls -l myapp.desktop。如果没有用户(u)的执行权限(x),可以使用chmod u+x myapp.desktop来添加权限。Exec字段可能有错误。例如,指定的可执行程序路径不存在,或者参数错误。可以通过文本编辑器打开.desktop文件,检查Exec字段的内容是否正确。gnome - session - quit命令退出当前会话,然后重新登录来解决可能的桌面环境故障。syslog或journalctl)journalctl命令来查看系统日志。在终端输入journalctl -xe,这会显示系统的最新日志,包括可能与应用程序启动(也就是双击.desktop文件尝试启动应用程序)相关的错误消息。可以通过查找与应用程序名称或者相关的关键词(如Exec,如果是.desktop文件中执行命令相关的错误)来定位问题。/var/log/syslog文件。使用文本编辑器(如gedit)打开文件,不过这个文件可能会比较大,重点查找与你双击的应用程序相关的时间戳附近的日志记录。GNOME Shell日志。可以通过在终端中运行journalctl -u gnome - shell来查看与GNOME Shell相关的日志。如果双击.desktop文件的问题是由于桌面环境组件处理不当引起的,可能会在这里找到线索。Nautilus)也可能有自己的日志或者调试模式。不过,这些日志可能不是默认开启的,需要一些额外的设置或者使用调试版本的软件来获取相关日志。GDM(GNOME Display Manager)、systemd - logind和GNOME Shell之间的交互出现了问题。GDM负责管理图形化登录界面,systemd - logind处理用户登录相关的系统服务,GNOME Shell是GNOME桌面环境的核心组件。df -h命令检查磁盘空间,确保有足够的可用空间。对于文件系统完整性,可以在启动时进入恢复模式(如果可以),运行文件系统检查工具,如fsck(具体命令根据文件系统类型而定,例如对于ext4文件系统,可以是fsck.ext4 /dev/sdaX,其中/dev/sdaX是你的根分区设备名称)。GDM、systemd - logind和GNOME Shell。在终端(如果可以通过其他方式进入,如使用恢复模式下的终端)中,先运行sudo apt - get update更新软件源,然后尝试sudo apt - get upgrade升级相关的软件包。如果问题仍然存在,可以考虑重新安装GDM,先使用sudo apt - get remove gdm卸载,再用sudo apt - get install gdm重新安装,但要注意这可能会导致配置丢失,最好提前备份相关的配置文件。~/.config目录下的文件)中。可以将原来用户的重要配置文件备份后,删除可能导致问题的配置文件,然后再尝试登录。.desktop文件是一种桌面入口文件,用于定义应用程序在桌面环境中的相关信息,其格式类似INI文件,主要包括以下几个部分:[]包围节名来表示。最重要的节是[Desktop Entry],它包含了应用程序的主要信息。键=值的形式来定义各种属性。[Desktop Entry]节中Name=Firefox。PATH环境变量来解析),还可以包含参数。如Exec=/usr/bin/firefox %u,其中%u是一个特殊的参数,表示URL,用于在启动浏览器时打开指定的URL。Icon=/usr/share/icons/hicolor/48x48/apps/firefox.png。Application(应用程序),也可以是Link(链接)或Directory(目录)。如Type=Application。;分隔。例如Categories=Network;WebBrowser会将应用程序归类到网络和网页浏览器类别中。Comment=A web browser for surfing the internet。startx命令来启动X会话(这会启动X Server并加载相关的桌面环境),不过这在现代桌面Linux系统中并不常见,因为系统一般是通过显示管理器(如GDM、LightDM等)来自动启动X Server和桌面环境。xinit命令,它可以初始化一个X Window System服务器并运行指定的客户端程序作为第一个应用程序。例如,xinit /usr/bin/gnome - session可以启动GNOME桌面环境对应的Display(这只是示例,实际命令可能因桌面环境和配置有所不同)。xhost命令可以在一定程度上控制对X Server的访问权限。如果普通用户在终端执行xhost +si: localuser: root,这会允许本地的root用户访问该用户的X Server显示。但这种操作存在安全风险,因为它放宽了访问控制,可能会使系统遭受恶意攻击。xhost命令是在X Server的客户端执行。xhost命令时,可以设置哪些用户或者主机能够连接到X Server,以此来管理访问显示资源的权限。例如,通过xhost +可以允许任何用户访问X Server,而xhost -会禁止其他用户访问。xhost命令中,+si:localuser:root这个参数用于添加(+表示添加权限)一个特定的访问规则。si代表“system information”(系统信息)。这个选项主要用于控制基于用户ID和组ID的主机访问。localuser:root部分表示允许本地(localuser)的root用户访问X Server。这种用法是在精细地控制哪些用户可以访问X显示服务,不过这种操作要谨慎使用,因为放宽访问权限可能带来安全风险。tkinter.Text控件是很好的选择。可以把脚本执行结果逐行插入到这个文本框中。它支持滚动显示大量文本内容。例如:import tkinter as tk
root = tk.Tk()
text_box = tk.Text(root)
text_box.pack()
# 假设result是脚本执行结果(字符串列表)
result = ["line1", "line2", "line3"]
for line in result:
text_box.insert(tk.END, line + "\n")
root.mainloop()
QTextEdit控件功能类似。它允许你设置为只读模式来显示文本内容,并且当内容超出显示范围时会自动出现滚动条。例如:from PyQt5.QtWidgets import QApplication, QTextEdit, QWidget
import sys
app = QApplication(sys.argv)
window = QWidget()
text_edit = QTextEdit()
text_edit.setReadOnly(True)
# 假设result是脚本执行结果(字符串列表)
result = ["line1", "line2", "line3"]
for line in result:
text_edit.append(line)
window.setLayout(text_edit)
window.show()
sys.exit(app.exec())
try - except块IOError或OSError异常。try:
file_obj = open("example.txt", "r")
content = file_obj.read()
print(content)
file_obj.close()
except (IOError, OSError):
print("文件对象无效或者文件操作出现问题")
Noneopen函数可能返回None。file_obj = open("nonexistent_file.txt", "r")
if file_obj is None:
print("文件对象无效")
else:
print("文件对象有效")
file_obj.close()
open函数遇到问题时更多是抛出异常,而不是返回None。isinstance函数(针对正确类型的文件对象)_io.TextIOWrapper(对于文本文件)或者其他相关的文件包装类型。import io
file_obj = open("example.txt", "r")
if isinstance(file_obj, io.TextIOWrapper):
print("文件对象是有效的文本文件对象")
file_obj.close()
def function_name(parameters):
"""函数文档字符串(可选)"""
# 函数体,包含执行的代码
return value(可选)
def关键字:用于定义一个函数,它是函数定义的开始标志。function_name:这是函数的名称,命名规则与变量命名规则相同,一般采用小写字母加下划线的方式(如my_function),方便阅读和理解。parameters:是函数的参数列表。参数可以有多个,用逗号隔开。如果没有参数,括号也不能省略。例如:def say_hello():def greet(name):def add_numbers(a, b):"""包围。它用于描述函数的功能、参数、返回值等信息,不是必须的,但良好的文档字符串有助于代码的维护和理解。return语句:用于返回函数的结果。如果函数不需要返回值,return语句可以省略。例如:def square(x):
return x * x
def print_message():
print("这是一条消息")
add_numbers:def add_numbers(a, b):
return a + b
a和b可以是整数、浮点数、字符串,甚至是自定义对象,只要这些对象定义了对应的加法操作(__add__方法)。result = add_numbers(2, 3),这里a = 2,b = 3,函数返回5。result = add_numbers("hello", " world"),此时a = "hello",b = " world",函数返回"hello world"。def add_numbers(a: int, b: int):
return a + b
1、-5、1000,可以进行加、减、乘、除等算术运算。3.14、-0.5,用于表示实数。a + bj,其中a是实部,b是虚部,例如2 + 3j。True和False两个值,用于逻辑判断,比如条件语句和循环控制。'或双引号"包围,如'hello'、"Python"。可以进行拼接、切片、查找等操作。[]表示,例如[1, 2, 3, 'a']。能进行添加、删除、修改元素等操作。()表示,如(1, 2, 3)。通常用于存储不希望被修改的数据。{}表示(空集合必须用set()创建),像{1, 2, 3}。主要用于去重和集合运算。{}表示,如{"name": "John", "age": 30}。通过键来访问值,用于存储和检索关联的数据。if 条件表达式:
# 条件满足时执行的代码块
语句1
语句2
else:
# 条件不满足时执行的代码块
语句3
语句4
age = 18
if age >= 18:
print("已成年")
else:
print("未成年")
if (条件表达式) {
// 条件满足时执行的代码块
语句1;
语句2;
} else {
// 条件不满足时执行的代码块
语句3;
语句4;
}
int age = 18;
if (age >= 18) {
System.out.println("已成年");
} else {
System.out.println("未成年");
}
if (条件表达式) {
// 条件满足时执行的代码块
语句1;
语句2;
} else {
// 条件不满足时执行的代码块
语句3;
语句4;
}
int age = 18;
if (age >= 18) {
printf("已成年");
} else {
printf("未成年");
}
if后面的条件表达式,如果条件为真(满足条件)就执行if分支下的代码块;如果条件为假(不满足条件)就执行else分支下的代码块。有些语言还支持else if来进行更多条件分支的判断呢。exit()和quit() ,但实际上它们并不是Python的内置函数,而是定义在site-packages模块中的函数。exit()或quit()函数时,程序会终止并退出。在大多数情况下,如果是在主程序中使用,它们的功能基本相同,都会引发SystemExit异常来终止程序。sys.exit()来退出程序,它是Python标准库sys模块中的函数。sys.exit()也会引发SystemExit异常,可以接收一个整数参数作为程序的退出状态码,通常0表示正常退出,非0表示异常退出 。例如:import sys
sys.exit(1)
not关键字 。例如:x = 5
if not x > 10:
print("x不大于10")
if条件not x > 10用于判断x是否不大于10,当此条件为真时,就会执行下面的打印语句 。 serial.Instance是否是合法的实例,通常可从以下几方面入手:isinstance() 函数serial.Instance所属的类叫SerialClass,你可以这样判断:if isinstance(serial.Instance, SerialClass):
print("是合法的SerialClass类的实例")
else:
print("不是合法的SerialClass类的实例")
SerialClass类有特定的属性,你可以检查serial.Instance是否有这些属性来判断其合法性。例如,SerialClass有个属性叫port,可这样检查:if hasattr(serial.Instance, 'port'):
print("可能是合法的实例,具有port属性")
else:
print("可能不是合法的实例,缺少port属性")
SerialClass有特定方法,可检查serial.Instance是否有该方法。如SerialClass有个方法叫open_connection(),可这样判断:if hasattr(serial.Instance, 'open_connection') and callable(serial.Instance.open_connection):
print("可能是合法的实例,具有可调用的open_connection方法")
else:
print("可能不是合法的实例,缺少open_connection方法或该方法不可调用")
serial.Instance的某个方法,根据是否引发异常来判断。如调用SerialClass的send_data()方法:try:
serial.Instance.send_data("test data")
print("可能是合法的实例,send_data方法调用成功")
except AttributeError:
print("可能不是合法的实例,缺少send_data方法")
except Exception as e:
print(f"调用send_data方法出错:{e}")
serial模块中,Serial 类的实例化及相关操作是可能会抛出异常的,以下是一些常见情况:ser = serial.Serial('COM3') ,若没有名为COM3的串口设备,就会抛出 SerialException异常。SerialException。比如在Linux下,非root用户可能没有权限打开特定串口设备。ser.open()时,会抛出SerialException 。ser.close()被多次调用,可能会引发异常,不过这取决于具体的serial模块实现。ser.read(10),如果规定时间内没读到10个字节,会抛出SerialTimeoutException 。SerialException 。import tkinter as tk
root = tk.Tk() # 创建根节点,即根窗口
text_box = tk.Text(root) # 创建文本框,并将其置于根窗口
text_box.pack()
root.mainloop() # 进入主事件循环,使窗口和部件保持显示状态
import tkinter as tk
root = tk.Tk()
# 创建文本框,并通过配置使其扩展填充整个根窗口
text_box = tk.Text(root)
text_box.pack(fill=tk.BOTH, expand=True)
root.mainloop()
pack方法的参数fill=tk.BOTH表示文本框在水平和垂直方向都填充根窗口,expand=True表示当根窗口大小改变时,文本框会随之扩展以充分利用空间 。这样文本框会占据根窗口的全部可用空间,看起来就好像二者合为一体了。 pack方法的参数设置有误,文本框可能无法正确填充根窗口。确保使用了fill=tk.BOTH和expand=True,且没有其他布局冲突。pack、grid和place等不同布局管理器,可能会导致布局混乱。尽量在一个项目中只使用一种布局管理器。import tkinter as tk
root = tk.Tk()
root.configure(bg='white')
text_box = tk.Text(root)
text_box.pack(fill=tk.BOTH, expand=True)
text_box.configure(bg='white')
root.mainloop()
io.BytesIO 类将字节(byte)数据转换为类文件流(stream)对象。以下是示例代码:import io
# 定义字节数据
byte_data = b'Hello, World!'
# 将字节数据转换为流对象
stream = io.BytesIO(byte_data)
# 可以像操作文件流一样操作这个流对象
print(stream.read())
io 模块,然后创建了字节数据 byte_data,最后使用 io.BytesIO() 将字节数据包装成了流对象 stream,并读取打印了其中的内容 。decode()方法,指定正确的编码格式即可将字节转换为字符串。如字节对象b采用UTF-8编码,可通过b.decode('utf-8')进行转换。常用的编码格式还有ASCII、GBK等,需根据字节数据的实际编码情况来选择。str()构造函数str()函数可将字节对象转换为字符串,需传入字节对象和编码格式两个参数,如str(b, 'utf-8')。若不指定编码格式,Python默认使用UTF-8编码。codecs模块codecs模块提供了更高级的编解码功能,通过codecs.decode()函数来解码字节对象。如import codecs; codecs.decode(b, 'utf-8') 。使用该模块可以更方便地处理一些复杂的编解码场景。 import tkinter as tk
root = tk.Tk()
root.withdraw() # 隐藏根窗口
text_box = tk.Text(root)
text_box.pack()
root.mainloop()
root.withdraw()语句用于隐藏根窗口,但程序仍在后台运行,文本框也能正常显示和使用 。若要在程序结束时还原根窗口的显示,可以在合适的位置添加root.deiconify()语句 。 update 方法:在一些GUI库中,如 tkinter,当你向文本框插入文本后,需要调用 update 方法来刷新界面,使更改立即显示。示例代码如下:import tkinter as tk
root = tk.Tk()
text_box = tk.Text(root)
text_box.pack()
text_box.insert(tk.END, "Hello, World!")
root.update()
root.mainloop()
see 方法:在 tkinter 中,如果插入文本后,文本框的可视区域没有自动滚动到新插入的文本位置,可以使用 see 方法来确保新添加的文本在可视范围内。例如:text_box.insert(tk.END, "New text\n")
text_box.see(tk.END)
root.withdraw()隐藏主窗口后,主窗口虽不可见但仍在后台运行,需添加相应代码来处理窗口关闭事件以实现完全退出程序,以下是几种解决方法:WM_DELETE_WINDOW协议方法来处理窗口关闭事件。当用户尝试关闭窗口时,此方法会被调用,在其中添加退出程序的逻辑,如root.destroy()。示例代码如下:import tkinter as tk
root = tk.Tk()
root.withdraw()
def on_close():
root.destroy()
root.protocol("WM_DELETE_WINDOW", on_close)
# 此处可添加其他组件及逻辑
root.mainloop()
atexit 模块atexit模块,在隐藏主窗口后,使用atexit.register()函数注册一个在程序退出时要执行的函数,如root.destroy(),示例如下:import tkinter as tk
import atexit
root = tk.Tk()
root.withdraw()
atexit.register(root.destroy)
# 此处可添加其他组件及逻辑
root.mainloop()
sys.exit()root.destroy(),还可调用sys.exit()来确保程序完全退出。需先导入sys模块,示例如下:import tkinter as tk
import sys
root = tk.Tk()
root.withdraw()
def on_close():
root.destroy()
sys.exit()
root.protocol("WM_DELETE_WINDOW", on_close)
# 此处可添加其他组件及逻辑
root.mainloop()
blkid command in the terminal. When you plug in the USB drive and run blkid, it will display information about all block devices including the USB drive. The output will look something like this: /dev/sdb1: UUID="12345678 - 9abc - def0 - 1234 - 56789abcdef0" TYPE="ext4"/etc/fstab file with root privileges. You can use a text editor like sudo nano /etc/fstab.UUID=12345678 - 9abc - def0 - 1234 - 56789abcdef0 /media/your - designed - path ext4 defaults 0 012345678 - 9abc - def0 - 1234 - 56789abcdef0 with the actual UUID of your USB drive and /media/your - designed - path with the path where you want to mount the USB drive. The ext4 should be replaced with the actual file system type of your USB drive (you can find this in the blkid output). The defaults option means it will use the default mount options, and the 0 0 at the end are dump and pass settings which are usually set to 0 for USB drives./etc/fstab file, you can test the configuration by unplugging and then plugging in the USB drive. It should now be mounted to the specified path./etc/fstab file, as incorrect entries can cause boot problems. Make sure you have a backup of the original file and double - check the entries before saving.udev installed. It's usually already installed on Ubuntu. udev is a device manager for the Linux kernel that can be used to handle device events such as USB device insertion.udevadm info -a -n /dev/sdX (replace sdX with the actual device node of your USB drive, like sdb). This will give you information such as the vendor ID, product ID, and other attributes.sudo nano /etc/udev/rules.d/10 - usb - mount.rules).ACTION=="add", ATTRS{idVendor}=="XXXX", ATTRS{idProduct}=="YYYY", SYMLINK+="your_desired_path/%k", RUN+="/bin/mount -t auto /dev/%k your_desired_path/%k"XXXX and YYYY with the actual vendor ID and product ID of the USB device you identified in step 1. You can find these values in the output of the udevadm command. The your_desired_path should be replaced with the actual path where you want to mount the USB device. For example, if you want to mount it to /media/usb - storage, you would use that path. The %k is a substitution for the device name (like sdb1).sudo udevadm control --reload - rules and then sudo udevadm trigger to apply the new rule immediately./etc/systemd/system/目录下,文件名一般以.service结尾,例如my_service.service。Description:简单描述服务的功能,如Description=My custom service。After:定义此服务应该在哪些其他服务启动之后再启动,例如After=network.target,表示这个服务在网络服务启动之后再启动。Type:定义服务的启动类型,常见的有simple(默认值,简单的前台进程)、forking(服务会调用fork()产生子进程,父进程退出)等。ExecStart:指定服务启动的命令,如ExecStart=/usr/bin/my_service_executable。Restart:定义服务意外退出后的重启策略,比如Restart=always表示服务总是重启。WantedBy:表明这个服务属于哪个目标(target),例如WantedBy=multi-user.target,这意味着当系统进入多用户模式时,这个服务会被启动。sudo systemctl daemon-reload重新加载systemd的配置文件,然后就可以用sudo systemctl start my_service来启动新定义的服务,用sudo systemctl enable my_service来设置服务开机启动。/etc/resolv.conf文件:这是传统的配置DNS服务器地址的文件。系统会读取其中的DNS服务器IP地址来进行域名解析。不过在现代Ubuntu系统(使用systemd - resolved服务的情况下),这个文件可能是由systemd - resolved动态生成的。systemd - resolved服务:这是Ubuntu系统用于管理网络名称解析的服务。它会从多种渠道获取DNS信息,包括DHCP服务器分配的DNS服务器地址等。可以通过systemctl status systemd - resolved查看它的状态。其配置文件在/etc/systemd/resolved.conf,但一般不建议直接修改这个文件,而是通过netplan工具间接修改。netplan:用于配置网络的工具,在/etc/netplan/*.yaml(通常是00 - installer - config.yaml或50 - cloud - init.yaml)文件中的nameservers部分可以配置DNS服务器地址。例如:network:
ethernet:
dhcp4: true
nameservers:
addresses: [8.8.8.8, 8.8.4.4]
sudo netplan apply使配置生效。getaddrinfo()函数(属于标准C库函数)。systemd - resolved或/etc/resolv.conf中指定的DNS服务)发送DNS请求,请求域名对应的IP地址。systemd - resolved时,如果系统中有两个网卡且对应不同的域名解析:systemd - resolved本身会根据系统的网络路由设置来选择合适的DNS服务器。一般来说,它会根据流量的路由方向来匹配对应的DNS服务器。netplan工具来对不同的网络接口指定不同的DNS服务器。在/etc/netplan/*.yaml文件中,可以分别为每个网络接口(网卡)设置不同的nameservers配置。例如:network:
version: 2
ethernet:
- interface: eth0
dhcp4: true
nameservers:
addresses: [8.8.8.8, 8.8.4.4]
- interface: eth1
dhcp4: true
nameservers:
addresses: [1.1.1.1, 1.0.0.1]
sudo netplan apply来使配置生效。这样可以一定程度上指定不同网卡对应的域名解析服务器。/etc/netplan/目录下,文件名可能是00 - installer - config.yaml、50 - cloud - init.yaml等,以.yaml为扩展名。sudo nano /etc/netplan/your - config - file.yaml)打开配置文件。network:
version: 2
ethernet:
- interface: eth0 # 网络接口名称,这里是eth0,你可以替换为实际的网卡名称
dhcp4: true # 是否使用DHCPv4
nameservers:
addresses: [8.8.8.8, 8.8.4.4] # 指定DNS服务器IP地址
network:
version: 2
ethernet:
- interface: eth0
dhcp4: true
nameservers:
addresses: [8.8.8.8, 8.8.4.4]
- interface: eth1
dhcp4: true
nameservers:
addresses: [1.1.1.1, 1.0.0.1]
sudo netplan apply,这会使新的网络配置生效,包括指定的DNS设置。yaml格式正确,否则可能导致配置无法正确应用。systemd - resolved服务状态sudo systemctl status systemd - resolved。在输出的信息中,会显示当前DNS服务器的相关信息。如果Netplan配置的DNS设置生效,这里应该能看到配置文件中指定的DNS服务器IP地址。DNS Servers部分可以看到类似8.8.8.8和8.8.4.4等配置好的DNS服务器IP地址。/etc/resolv.conf文件内容systemd - resolved服务的情况下,/etc/resolv.conf文件通常是由systemd - resolved自动生成的。运行cat /etc/resolv.conf查看文件内容。nameserver后面跟着Netplan配置的DNS服务器IP地址。不过要注意,在某些特殊情况下,这个文件可能会被其他工具或配置覆盖,但在正常的systemd - resolved环境下,它会反映Netplan的配置。dig命令进行测试dig是一个用于查询DNS相关信息的强大工具。例如,如果你想测试域名example.com的DNS解析,可以运行dig example.com。;; SERVER:部分,可以看到实际用于解析该域名的DNS服务器IP地址。如果这个地址与Netplan配置的一致,就说明配置生效了。例如,如果Netplan配置了8.8.8.8作为DNS服务器,这里看到的SERVER的IP地址应该是8.8.8.8。tcpdump)查看,发现DNS请求是发送到Netplan配置的DNS服务器的,那么也可以证明配置生效。不过这种方法相对复杂,需要对网络抓包工具有一定的了解。nmcli命令nmcli dev show | grep 'ip4.dns',此命令会显示当前正在使用的DNS服务器地址,通过查看与特定网卡对应的DNS地址,即可知晓其获得的DNS服务器IP地址.systemd-resolve命令systemd-resolve --status | grep 'dns servers',该命令会显示系统当前正在使用的DNS服务器,如果配置了多个DNS服务器,也会全部显示,从中可找到特定网卡所使用的DNS服务器IP地址.resolvectl命令resolvectl status,能查看全局DNS信息以及各个网卡的DNS信息,从而确定特定网卡所对应的DNS服务器IP地址.DnsResolver类来进行DNS解析,应用程序可调用DnsResolver.getInstance().query(hostname)来获取域名对应的IP地址列表.usable_servers()中。如果所有服务器都不可用,则会将所有服务器标记为可用,以确保域名解析能够进行.ndc resolver setifdns eth0 dns1可设置指定网络接口的DNS.gethostbyname函数gethostbyname是一个传统的用于进行主机名到IP地址解析的函数,它在libc(C标准库)中。在早期的Linux系统以及一些简单的应用场景中,应用程序可能会直接调用gethostbyname。/etc/hosts文件和/etc/resolv.conf文件等)来查找主机对应的IP地址。例如,如果/etc/hosts文件中有主机名和IP地址的映射记录,gethostbyname首先会查看这个文件来进行解析。gethostbyname函数存在一些局限性。它是一个阻塞式的函数,在进行域名解析时,如果DNS服务器响应较慢或者网络出现问题,整个应用程序可能会被阻塞在这个函数调用上,等待解析结果。而且它不支持一些现代的DNS特性,如DNSSEC(域名系统安全扩展)等。resolvctl等工具)resolvctl是用于管理系统DNS解析配置的工具。系统的DNS服务(如systemd - resolved)会按照/etc/resolv.conf等配置文件中的设置,与DNS服务器进行通信来进行域名解析。systemd - resolved来缓存DNS解析结果,提高解析效率,并且可以对DNS查询进行加密(如通过DNS - over - TLS)来提高安全性。gethostbyname,尤其是那些没有更新以适应现代系统DNS管理机制的程序。但大多数现代的、遵循良好编程实践的应用程序会使用系统提供的标准网络库函数来进行DNS查询,这些函数会间接利用系统的DNS服务。nsswitch.conf(名称服务切换配置文件)交互,根据配置来决定是使用/etc/hosts文件、DNS服务器还是其他名称服务来进行主机名解析。这种方式比直接调用gethostbyname更加灵活和安全。gethostbyname,但这不是一种推荐的现代做法,大多数应用应该使用系统提供的DNS服务机制来进行域名解析。gethostbyname函数调用。这是最直接的方法。例如,在C/C++代码中,使用文本搜索工具查找gethostbyname字符串。如果发现有这样的函数调用,那么很可能应用程序在这部分代码中使用了这个函数进行域名解析。ldd(在Linux系统中用于查看程序运行时所需的共享库)来查看应用程序依赖的库。如果应用程序依赖于包含gethostbyname函数的libc库,这增加了它可能使用这个函数的可能性。但是,仅仅依赖libc并不意味着一定会使用gethostbyname,因为libc还提供了许多其他功能。gethostbyname函数。如果调用了这个函数,GDB会显示函数调用的栈信息,帮助确定调用路径。strace是一个用于跟踪系统调用和信号的工具。运行strace -e gethostbyname <应用程序名称>可以只跟踪gethostbyname系统调用。如果应用程序在运行过程中调用了这个函数,strace会显示相关的调用信息,包括参数和返回值。不过要注意,有些库函数可能会在内部进行系统调用,而strace只能跟踪到系统调用级别。systemd - resolved的接口),那么有可能它是使用自己的方式(如gethostbyname)进行域名解析。不过,这种方法需要对DNS协议和网络流量有一定的了解,因为区分应用程序自身的DNS查询和系统的DNS查询可能比较复杂,尤其是在系统同时进行其他网络活动的情况下。/var/log/syslog或journalctl输出):某些系统会在日志中记录DNS相关的活动。如果应用程序使用系统的DNS服务,可能会在日志中看到相应的记录,如systemd - resolved的日志信息,显示应用程序请求DNS解析的记录。如果没有这些系统DNS服务相关的日志记录,而应用程序又进行了域名解析,可能是使用了其他方式,如gethostbyname。gethostbyname函数或者绕过系统DNS服务的操作。dig命令本身不能直接指定使用哪一个网络设备来查询域名,但可以通过指定查询使用的源IP地址来间接选择网络设备,nslookup命令也有类似的功能,以下是具体介绍:-b参数指定源IP地址:dig命令的-b参数可以设置查询的源IP地址,通过指定特定网络设备所绑定的IP地址作为源IP,从而使查询请求从该网络设备发出。例如,如果你的机器有两个网络接口,分别绑定了IP地址192.168.1.10和10.0.0.20,你想使用绑定192.168.1.10的网络设备来发送查询请求,可以使用命令dig -b 192.168.1.10 example.com.@参数指定DNS服务器:如果不指定@参数,dig会按照/etc/resolv.conf中的配置来选择DNS服务器进行查询。若要使用特定的DNS服务器,可以在命令中使用@参数指定,如dig @8.8.8.8 example.com,这样查询请求就会被发送到指定的DNS服务器1.ifconfig或ip addr show查看网络设备和IP地址:在使用nslookup指定网络设备之前,需要先查看网络设备的名称和对应的IP地址。可以使用ifconfig或ip addr show命令来查看,例如ip addr show会列出系统中的网络接口及其相关信息,包括IP地址、子网掩码等3.dig类似,nslookup本身也没有直接指定网络设备的参数,但可以通过指定源IP地址来选择网络设备。进入nslookup的交互模式后,使用server命令指定要查询的域名服务器,然后使用set source=源IP地址命令设置源IP地址,之后的查询就会从该IP地址所在的网络设备发出。例如:nslookup
> server 8.8.8.8
> set source=192.168.1.10
> example.com
8.8.8.8,然后设置源IP地址为192.168.1.10,最后查询example.com的域名解析信息 。-i或--interface参数指定网络接口:host命令可以使用-i或--interface参数来指定查询使用的网络接口。例如,如果你的网络接口是eth0,可以使用命令host -i eth0 example.com来通过eth0网络接口查询example.com的域名解析2.host命令是一个简单的域名查询工具。它可以用于查询域名对应的IP地址,也可以进行反向查询(即从IP地址查询域名)。例如,host example.com会返回域名example.com对应的IP地址信息。如果要进行反向查询,如查询IP地址192.0.2.1对应的域名,可以使用host 192.0.2.1。host命令还可以查询域名的其他信息,如域名的邮件服务器(MX记录)。例如,host -t MX example.com会返回example.com域名的邮件服务器记录,这些记录对于邮件系统的配置和故障排查非常有用。whois命令主要用于查询域名的注册信息。当你输入一个域名作为参数时,它会返回该域名的注册商、注册日期、过期日期、所有者信息等。例如,whois example.com会显示example.com域名的详细注册情况,包括注册人姓名、组织、联系方式(可能部分信息因隐私保护而隐藏)以及域名服务器信息等。whois命令也可以用于查询IP地址段的相关信息。对于网络管理员来说,这有助于了解IP地址的分配情况和所属机构。例如,whois 192.0.2.0/24可以查询这个IP地址段的所有者、分配范围等信息。drill是一个类似dig的DNS查询工具,它也是用于查询域名系统(DNS)信息的命令行工具。drill命令的输出格式比较简洁明了,它支持多种DNS记录类型的查询,如A记录、AAAA记录、MX记录、NS记录等。drill example.com会查询example.com域名的A记录(即域名对应的IP地址),并且以比较简洁的格式显示查询结果。drill -t MX example.com则会查询example.com域名的邮件服务器(MX)记录。systemd-resolved服务缓存的DNS解析内容的刷新时间取决于DNS记录中的生存时间(TTL)值,一般默认的TTL值在不同的域名和DNS服务器配置下有所不同,从几分钟到几小时甚至几天都有可能 。以下是一些强制刷新systemd-resolved服务DNS缓存的方法24 :sudo systemd-resolve --flush-caches来清除systemd-resolved服务的DNS缓存,执行该命令后,系统会在下次需要进行DNS查询时重新获取最新的解析结果,而不是使用缓存中的旧数据 。sudo systemctl restart systemd-resolved命令重启systemd-resolved服务,这样在服务重启的过程中会清除缓存,并在重新启动后重新建立DNS缓存,从而获取最新的DNS解析信息 。systemd-resolved服务DNS缓存的方法 。systemd - resolved服务的DNS缓存刷新时间主要是依据DNS记录中的生存时间(TTL)来确定的。TTL是由域名的权威DNS服务器设置的,它表示DNS记录在缓存中的有效时间。例如,一个域名的A记录(IP地址记录)的TTL设置为3600秒,那么systemd - resolved服务会在缓存该记录后的3600秒后尝试刷新它。systemd - resolve命令查看单个域名的缓存信息:systemd - resolve --statistics命令查看DNS解析的统计信息,其中包括缓存命中次数等,但没有直接显示每个域名缓存的TTL。systemd - resolve --query=域名命令。例如,systemd - resolve --query=example.com会显示example.com域名的解析结果,包括其IP地址和缓存相关的信息。在输出结果中,可能会有类似于“Cache lifetime”或“TTL”的字段显示当前缓存记录的剩余有效期,但这可能因systemd - resolved的版本不同而有所差异。/run/systemd/resolve/stub - resolver.conf文件(间接方式):systemd - resolved服务会生成一个stub - resolver.conf文件,该文件用于配置系统的DNS解析行为。虽然它没有直接显示缓存的刷新时间,但可以查看其中的DNS服务器信息等内容。例如,通过cat /run/systemd/resolve/stub - resolver.conf命令查看,其中的nameserver行显示了当前使用的DNS服务器,这有助于理解DNS解析的来源,并且可以通过查询该DNS服务器上域名的TTL来推测缓存刷新时间。systemd - resolved服务的调试日志来查看更详细的缓存信息,包括缓存的更新和刷新情况。首先,编辑/etc/systemd/resolved.conf文件,将LogLevel选项设置为debug,然后重启systemd - resolved服务。之后,通过查看journalctl - u systemd - resolved的日志输出,可以找到有关DNS缓存更新、查询以及TTL相关的详细信息。不过,这种方法会产生大量的日志信息,需要仔细筛选和分析。systemd - resolve命令查看缓存记录systemd - resolve --statistics来查看DNS解析的统计信息,其中包括缓存相关的内容。它会显示缓存命中次数(Cache Hits)、缓存未命中次数(Cache Misses)等信息。不过,这个命令不会详细列出每个域名的缓存记录内容。systemd - resolve --query <域名>命令来查看特定域名的缓存记录。例如,如果要查看example.com的缓存记录,可以使用systemd - resolve --query example.com。输出结果会包含域名对应的IP地址(如果有)、解析来源(如From cache表示从缓存获取)、DNS服务器信息等。它还可能显示缓存记录的剩余生存时间(TTL)相关信息,这有助于了解缓存记录的时效性。/run/systemd/resolve/stub - resolver.conf文件(辅助方式)systemd - resolved服务生成的,用于配置系统的DNS解析行为。虽然它本身不直接展示缓存记录,但可以通过查看其中的DNS服务器信息,了解系统是从哪些DNS服务器获取解析结果并进行缓存的。使用cat /run/systemd/resolve/stub - resolver.conf命令查看文件内容,重点关注nameserver行,它列出了正在使用的DNS服务器。/etc/systemd/resolved.conf文件,将LogLevel选项设置为debug。然后重启systemd - resolved服务。journalctl - u systemd - resolved的日志来获取更详细的缓存信息。在日志中,会记录每次DNS查询、缓存命中或未命中的情况,以及缓存记录的更新和清除等操作。不过这种方法会产生大量的日志内容,需要仔细筛选和分析相关的缓存记录条目。systemd - resolved服务状态systemctl命令来查看systemd - resolved服务的状态。运行sudo systemctl status systemd - resolved,这会显示服务是否正在运行、最近的启动时间等基本信息。如果服务没有正常运行,可能无法正确缓存DNS记录。systemd - resolve命令,运行systemd - resolve --statistics来查看DNS解析的统计信息。在Ubuntu下,这个命令会输出如缓存命中次数(Cache Hits)、缓存未命中次数(Cache Misses)、DNS服务器查询次数(DNS Server Queries)等内容,帮助你了解DNS缓存的使用效率。systemd - resolve --query <域名>命令。例如,要查看google.com的缓存记录,运行systemd - resolve --query google.com。输出会包含域名对应的IP地址、解析来源(是否从缓存获取)、DNS服务器相关信息等内容,在Ubuntu下此命令的功能和在其他基于systemd的系统中类似。systemd - resolved相关配置文件/run/systemd/resolve/stub - resolver.conf文件了解DNS配置信息。在Ubuntu中,可以使用cat /run/systemd/resolve/stub - resolver.conf来查看,其中nameserver行显示了当前使用的DNS服务器,这对理解DNS缓存来源有帮助。/etc/systemd/resolved.conf文件,将LogLevel选项设置为debug。在Ubuntu中,重启systemd - resolved服务可以使用sudo systemctl restart systemd - resolved。journalctl - u systemd - resolved查看日志来获取详细的缓存信息,日志会记录DNS查询、缓存命中或未命中等情况,不过这种方法会产生大量日志,需要仔细筛选。resolvectl命令,而其他一些Linux发行版可能使用systemd-resolve命令13.以下是resolvectl的一些常见用法:resolvectl statistics命令来查看DNS解析的统计信息,如缓存命中次数、未命中次数等,示例如下:resolvectl statistics
resolvectl query <域名>命令来查看特定域名的缓存记录,例如:resolvectl query google.com
sudo resolvectl flush-caches
resolvectl命令修改DNS服务器之前,首先可以查看当前的DNS服务器配置。使用resolvectl status命令,它会显示当前网络接口的DNS配置信息,包括使用的DNS服务器地址、域名搜索列表等。例如,输出可能会显示类似“Current DNS Server: 8.8.8.8”这样的信息,表示当前正在使用的DNS服务器是8.8.8.8。resolvectl dns <接口名称> <DNS服务器地址>命令。如果要为所有网络接口添加DNS服务器,可以将接口名称设置为“.”。例如,要添加8.8.8.8作为DNS服务器,可以使用resolvectl dns. 8.8.8.8。ip addr show命令来查看网络接口名称和对应的IP地址等信息。假设网络接口名称为“eth0”,要添加1.1.1.1作为该接口的DNS服务器,可以使用resolvectl dns eth0 1.1.1.1。resolvectl dns <接口名称> ""命令来删除DNS服务器。如果要从所有网络接口删除DNS服务器,可以将接口名称设置为“.”。例如,resolvectl dns. ""会清除所有网络接口的DNS服务器配置,这可能会导致系统无法进行正常的DNS查询,除非有其他备用的DNS解析方式(如本地/etc/hosts文件)。resolvectl dns eth0 ""。resolvectl本身没有直接修改DNS服务器顺序的命令,但可以通过先删除再添加的方式来调整顺序。例如,如果有两个DNS服务器8.8.8.8和9.9.9.9,当前顺序是先使用8.8.8.8,要将9.9.9.9放在前面,可以先删除两个服务器(resolvectl dns. ""),然后按照希望的顺序添加(先添加9.9.9.9,再添加8.8.8.8)。resolvectl会根据网络配置文件和系统设置自动确定DNS服务器的优先级。在某些情况下,通过修改/etc/netplan/*.yaml(Ubuntu使用Netplan进行网络配置)等网络配置文件,也可以间接影响DNS服务器的优先级和配置。例如,在Netplan配置文件中,可以指定特定网络接口的DNS服务器,这些设置会在系统启动时或重新应用Netplan配置时被resolvectl采用。www.example.com 解析到服务器的IPv4地址 192.0.2.1123.www.example.com 解析到 IPv6地址 2001:0db8:85a3:0:0:8a2e:0370:733412.alias.example.com 的CNAME记录,指向 www.example.com,当访问 alias.example.com 时,会自动跳转到 www.example.com 对应的服务器123.example.com 的MX记录,指向邮件服务器 mail.example.com,邮件系统就会知道将发送到 example.com 的邮件投递到指定的邮件服务器3.example.com 创建ALIAS记录,将流量路由到 www.example.com 或其他AWS资源1.www.example.com 这样的域名解析到对应的IPv4地址123.www.example.com 解析到 IPv6地址 2001:0db8:85a3:0:0:8a2e:0370:73341.alias.example.com 的CNAME记录,指向 www.example.com,当访问 alias.example.com 时,会自动跳转到 www.example.com 对应的服务器。需要注意的是,CNAME记录不能用于DNS命名空间的顶级节点12.example.com 的MX记录,指向邮件服务器 mail.example.com,邮件系统就会知道将发送到 example.com 的邮件投递到指定的邮件服务器13.www.example.com)映射到一个IPv4地址(例如192.168.1.1)。当用户在浏览器中输入域名时,DNS服务器会查找A记录来确定要访问的服务器的IP地址。203.0.113.10,要使域名www.company.com能够访问这个服务器,就需要在DNS服务器中为www.company.com创建一个A记录,将其指向203.0.113.10。2001:0db8:85a3:0000:0000:8a2e:0370:7334。2001:db8::1,要让域名www.exampleipv6.com能够访问这个服务器,就需要为该域名创建一个AAAA记录,指向2001:db8::1。alias.example.com可以通过CNAME记录指向www.example.com。example.com本身,不能直接用CNAME记录来设置别名)。campaign1.example.com、campaign2.example.com等,它们都可以通过CNAME记录指向www.example.com,这样所有这些域名都可以访问公司的主网站。example.com由某DNS服务提供商托管,该服务提供商的DNS服务器名称是ns1.provider.com和ns2.provider.com,那么就需要为example.com设置NS记录,分别指向ns1.provider.com和ns2.provider.com。example.com,如果邮件服务器是mail.example.com,并且优先级为10,那么就需要为example.com创建一个MX记录,将优先级设置为10,指向mail.example.com。如果有多个邮件服务器,可以设置不同的优先级,邮件首先会尝试发送到优先级最高的服务器。example.com的SPF TXT记录可以是v=spf1 ip4:192.168.1.1 -all,这表示只有来自192.168.1.1这个IP地址的邮件才被允许使用example.com这个域名发送。example.com可以设置CAA记录,如0 issue "letsencrypt.org",这表示只允许Let's Encrypt这个CA为该域名颁发证书。+1 - 202 - 555 - 0100可以通过NAPTR记录转换为一个域名,然后通过这个域名访问相关的电信服务。192.168.1.1,对应的域名是server.example.com,那么在反向DNS区域中,需要为192.168.1.1创建一个PTR记录,将其指向server.example.com。ns1.example.com,管理员邮箱admin.example.com(通常写成admin.example.com.,最后的点表示完整的域名),以及序列号等信息。v=spf1 ip4:192.168.1.1 -all表示只有来自192.168.1.1这个IP地址的邮件才被允许使用example.com这个域名发送。im.example.com,如果服务服务器的IP地址是192.168.1.2,端口是5222,可以创建一个SRV记录,指定服务_xmpp - client._tcp.im.example.com,优先级为10,权重为10,端口为5222,指向192.168.1.2。example.com创建一个ALIAS记录,直接指向一个CloudFront分发资源,使得用户访问example.com时能够直接通过CloudFront来获取内容。bind9、dnsmasq等常见的DNS服务器软件并进行安装配置。以dnsmasq为例,安装完成后,编辑其配置文件,通常是/etc/dnsmasq.conf。8.8.8.8和8.8.4.4或国内的114.114.114.114等。dnsmasq设置为监听WireGuard服务器的虚拟网络接口,通常在配置文件中指定interface选项,设置为WireGuard的接口名称,如wg0。DNS字段,指定为WireGuard服务器端的IP地址。例如,如果WireGuard服务器的内部IP地址是10.0.0.1,则在客户端配置文件的[Interface]部分添加DNS = 10.0.0.1。dnsmasq之类的DNS服务器软件。8.8.8.8时,客户端通过WireGuard连接到服务器后,其DNS请求会被服务器转发至8.8.8.8进行解析。这种方式简单直接,适用于大多数情况,能利用谷歌DNS服务器的稳定性和高效性来快速获取域名解析结果。dnsmasq等DNS服务器软件的好处在于可以更灵活地配置DNS解析规则。比如,可以在本地缓存经常访问的域名解析结果,提高解析速度;可以设置自定义的域名解析规则,将特定域名解析到指定的内部服务器IP地址等。.conf为扩展名),在[Interface]部分添加或修改DNS字段,指定为你想要使用的DNS服务器IP地址,如WireGuard服务器端的IP地址或其他公共DNS服务器地址,多个地址可用逗号分隔。[Interface]部分设置DNS选项,指定所需的DNS服务器IP地址。/etc/resolv.conf文件,将原有DNS服务器配置注释掉或删除,添加新的DNS服务器地址,即WireGuard虚拟设备所使用的DNS服务器地址。sudo systemctl restart network-manager或sudo service networking restart等,具体命令因Linux发行版而异,使网络配置生效。resolvectl命令来查看和修改网络设备的DNS服务器设置,以下是具体操作:resolvectl status命令,会列出系统中所有网络接口的DNS配置信息,包括当前使用的DNS服务器地址等。resolvectl命令结合网络设备名称来操作。例如,要将eth0网络接口的DNS服务器设置为8.8.8.8和8.8.4.4,可在终端中输入sudo resolvectl dns eth0 8.8.8.8 8.8.4.4。若要删除eth0原来的DNS设置,可输入sudo resolvectl dns eth0 ""或sudo resolvectl dns eth0 "none",这将清空该接口的DNS服务器列表。systemd-networkd的系统,可编辑/etc/systemd/network/*.network文件,在对应的网络接口配置段中添加或修改DNS选项。对于使用NetworkManager的系统,可通过nmcli命令或编辑/etc/NetworkManager/NetworkManager.conf等文件来设置。resolvectl status命令来查看修改后的DNS服务器设置是否生效。8.8.8.8作为DNS服务器,那么当收到客户端的DNS请求时,服务器会将该请求原封不动地转发到配置好的DNS服务器进行解析。dnsmasq、bind9等。这些工具可以根据配置规则来处理客户端的DNS请求,例如可以设置缓存、自定义域名解析规则、转发到不同的DNS服务器等。sshd服务时会生成自己的私钥KEYser-pri和公钥KEYser-pub,客户端发起ssh请求后,服务器将公钥发送给客户端,客户端将其存放于~/.ssh/known_hosts下,并生成自己的公私钥KEYcli-pub和KEYcli-pri,然后回传公钥到服务器,之后双方就可以使用公私钥加密通信了。ssh -L 8080:db.example.com:3306 user@ssh-server.com表示将远程db.example.com上的3306端口映射到本地的8080端口,本地应用访问本地8080端口的数据会通过SSH隧道传输到远程服务器的3306端口。ssh -R 9090:localhost:3000 user@ssh-server.com,会让远程ssh-server.com上的9090端口访问本地运行在3000端口的服务。ssh -D 8080 user@ssh-server.com,客户端通过SOCKS代理将请求发送到SSH服务器,再由服务器转发到目标服务器。socat和sslh等工具来实现。如在服务器端,可先配置sslh监听443端口,将HTTPS流量转发到本地的8443端口,将WireGuard流量转发到本地的51820端口;再使用socat将接收到的TCP 443端口的流量转换为UDP 51820端口的流量并发送给WireGuard服务器。socat和sslh的不同版本在不同操作系统上的表现可能不一致,可能导致连接不稳定或无法正常工作。ListenPort = 51820这一行修改为ListenPort = 443或其他你想要的UDP端口号,从而改变其监听端口。listening port改为443,可能会与默认的SSH服务端监听端口(通常为22)不冲突,但与可能运行在443端口的其他服务会产生冲突,导致启动失败或运行异常,以下是具体情况:/etc/named.conf文件中的listen-on port 53配置项是否正确设置。iptables,可添加如下规则允许DNS流量通过:iptables -A INPUT -p udp --dport 53 -j ACCEPT;iptables -A OUTPUT -p udp --sport 53 -j ACCEPT。nslookup或dig命令进行DNS查询测试,指定Wildguard服务器的IP地址作为DNS服务器,查看是否能正常解析域名。例如,在Linux系统中可使用dig @<Wildguard服务器IP> example.com命令进行测试。ping命令测试客户端与Wildguard服务器之间的网络连接,确保两者之间能够正常通信。/etc/wireguard/client.conf或类似路径。(Interface)部分找到DNS这一行,将其值修改为Wildguard服务端的IP地址,如DNS = 192.168.1.1 。wg-quick up <配置文件名>命令启动客户端连接,如wg-quick up client。sudo apt-get install wireguard命令安装;对于基于Red Hat或CentOS的系统,使用sudo yum install wireguard命令安装。/etc/wireguard/目录下,文件名一般为client.conf或类似名称。如果没有,可根据实际情况创建一个新的配置文件。[Interface],设置客户端的私钥PrivateKey,私钥可由wg genkey命令生成。[Interface]部分添加或修改DNS选项,将其值设置为Wildguard服务端的IP地址,如DNS = 192.168.1.100。可同时设置多个DNS服务器地址,用空格分隔。wg-quick up <配置文件名>命令启动客户端连接,如wg-quick up client.conf。sudo systemctl enable wg-quick@<配置文件名>命令,将<配置文件名>替换为实际的配置文件名。wg命令查看WireGuard连接状态,如wg show,可查看接口是否已启动、连接的对等体等信息。nslookup或dig命令进行DNS查询测试,如nslookup google.com或dig google.com,查看是否能通过Wildguard服务端正确解析域名。ip route命令修改系统默认路由(default route)可以按照以下步骤进行:ip route show或ip route list命令,查看当前系统的路由表,找到默认路由的相关信息,如默认网关等。sudo ip route del default
sudo ip route add default via <新网关IP地址> dev <出接口名称>
sudo ip route add default via 192.168.1.1 dev eth0
192.168.1.1是新的默认网关IP地址,eth0是网络出接口名称,需要根据实际情况进行替换。ip route show或ip route list命令查看修改后的路由表,确认默认路由已成功修改。sys/syscall.h、sys/socketcall.h等。fork()、execve()等。mmap()、munmap()等。open()、read()、write()等。socket()、bind()、listen()等。sudo ubuntu-drivers list 或sudo ubuntu-drivers devices,会列出与硬件适配的可用Nvidia显卡驱动版本。sudo ubuntu-drivers autoinstall,该命令会自动检测并安装最适合硬件的推荐驱动版本。sudo ubuntu-drivers install nvidia:535 命令。sudo apt install linux-modules-nvidia-${driver_branch}${server}-${linux_flavour} 命令安装。sudo apt install nvidia-driver-(version_number)命令安装具体版本的驱动元包。lsmod命令:在终端中输入lsmod | grep nvidia,如果输出类似于nvidia_uvm 901120 0 、nvidia_drm 40960 4等内容,则表示驱动程序已成功加载。nvidia-smi命令:在终端中输入nvidia-smi,如果成功安装,会显示Nvidia显卡的详细信息,包括显卡型号、驱动版本、GPU使用率、温度等。cat /proc/driver/nvidia/version命令:在终端中输入此命令,会显示已安装的Nvidia驱动的版本信息。sudo dpkg --list | grep nvidia-*命令:该命令可以列出系统中已安装的所有与Nvidia相关的软件包,如果有正常的显示,则说明驱动安装成功。glxinfo | grep rendering命令:在终端中输入此命令,如果结果是yes,说明显卡驱动已经成功安装。如果上述指令运行不成功,可能是因为系统里面没有安装mesa-utils,可以使用sudo apt-get install mesa-utils安装后再运行该命令 。sudo lshw -c video,查看输出结果中的“configuration”一行,如果有driver=nvidia的字符串,那么就说明Nvidia的驱动安装成功 。星辰大海捞针 / 豆包
墨舞的词可以是
宣纸铺墨香浮
笔锋婉转如龙舞
黑白间乾坤殊
挥洒豪情意难书
曲就用传统五声音阶
加上古筝和竹笛伴奏
中间来段京剧念白
比如且看这墨韵
尽显风流处
星辰大海捞针 / 豆包
挥毫落纸墨香漫
纸墨笔砚韵相连
黑白世界神韵展
浓淡干湿韵味添
笔走龙蛇心手牵
墨染诗意情万千
诗意盎然墨如幻
挥洒自如似神仙
笔情墨韵诗意添
墨染千秋韵万千
浓墨重彩诗意显
挥洒自如天地间
笔酣墨饱韵味长
墨染诗意心飞扬
诗意盎然墨如流
泼墨挥毫书辉煌
笔情墨韵诗意添
墨染千秋韵万千
轻描淡写诗意现
行云流水天地间
笔情墨韵诗意添
墨染千秋韵万千
笔走龙蛇诗意显
挥洒自如天地间
| 时间 | 7:00 | 7:15 | 7:30 | 7:45 | 8:00 |
|---|---|---|---|---|---|
| 时间 | 8:15 | 8:30 | 9:00 | 9:30 | 10:00 |
| 时间 | 10:30 | 11:00 | 11:30 | 12:00 | 12:30 |
| 时间 | 13:00 | 13:30 | 14:00 | 14:30 | 15:00 |
| 时间 | 15:30 | 16:00 | 16:30 | 17:00 | 17:30 |
| 时间 | 18:00 | 18:30 | 19:00 | 19:30 | 20:00 |