android-ndk開發(9): undefined reference to `__aarch64_ldadd4_acq_rel` 報錯分析

1. 概要

基礎庫 libbase.a 基于 android ndk r18b 編譯, 被算法庫 libfoo.so 和算法庫 libbar.a 依賴, 算法庫則分別被 libapp1.so 和 libapp2.so 依賴。

libapp1.so 的開發者向 libfoo.so 的開發者反饋了鏈接報錯:

error: undefined symbol: __aarch64_ldadd4_acq_rel

libapp2.so 的開發者向 libbar.a 的開發者反饋了鏈接報錯:

undefined reference to `__aarch64_ldadd4_acq_rel'

libapp2.so 的開發者通過升級 NDK 版本解決了問題。 由于沒有 libbar.a 和 libapp2.so 對應的 ndk 詳細版本和最小復現代碼,

在搜索引擎上以 “undefined reference to `__aarch64_ldadd4_acq_rel’” 為關鍵字找到相似案例并分析, 確定了升級 NDK 能消除上述鏈接報錯的原因。

2. opencv issue 24856

2.1 報錯描述

https://github.com/opencv/opencv/issues/24856 (參考鏈接[1])

用戶 kevinzezel 在 android 平臺, 使用 OpenCV 4.9.0 + ncnn, 遇到鏈接報錯, 而使用 OpenCV 4.5.5~4.8.0 時沒有報錯。 報錯信息是:

undefined reference to `__aarch64_ldadd8_acq_rel’

opencv 維護人員 asmorkalov 提議讓用戶開啟 -mno-outline-atomics 編譯選項, 用戶 kevinzezel 反饋說 ndk 21.4.7075529 不支持這一選項.

catboost 維護者 andrey-khropov 說, 很可能是 clang 13.0.0-rc1 版本引入的問題, 對應到 commit: https://github.com/llvm/llvm-project/commit/c5e7e649d537067dec7111f3de1430d0fc8a4d11 (參考鏈接[2])。 解決方法: 要么使用低版本 clang (< 13.0.0), 要么用高版本 clang 但是傳入 -mno-outline-atomics 選項。

用戶 bvnp43 說, 升級 ndk 到 26.2.11394342 后問題解決。

用戶 chenyan-master 說, 編譯 V8 時遇到類似問題 (ndk 22.0.7026061), 升級 ndk 版本解決了。

2.2 分析

ncnn 版本沒有被提及, 大概率是沒有變化。 OpenCV 從 4.8.0 到 4.9.0 引發了鏈接報錯, 猜測是因為 OpenCV 官方編譯 android sdk 時更換了 ndk 版本, 而 ndk 版本和 clang 版本有一定的對應關系。

https://stackoverflow.com/questions/53385892/find-the-ndk-version-used-for-building-opencv-android-native-libraries (參考鏈接[3]) 給出了從 OpenCV 靜態庫反推編譯他它的 ndk 版本、 ndk 里的 clang 版本的方法:

strings libopencv_core.a | ag "Android NDK"
strings libopencv_core.a | ag "C++ Compiler"
opencvndkclang
4.9.025.2.951965314.0.7
4.8.018.1.50630457.0.2

ndk 和 clang 的版本對應關系, 則通過 clang++ --version 確定, e.g.

D:/soft/android-ndk/r21e/toolchains/llvm/prebuilt/windows-x86_64/bin/clang++ --version

ndk 的數字形式的 x.y.z 版本, 和字母形式的版本如 r21e, 則通過 <ndk-目錄>/source.properties 確定, 例如 ndk-r21e:

Pkg.Desc = Android NDK
Pkg.Revision = 21.4.7075529

整理后的 ndk 和 clang 版本對應關系如下:

ndkndkclang
r28b28.1.1335670919.0.0
r27c27.2.1247901818.0.3
r26d26.3.1157926417.0.2
r25c25.2.951965314.0.7
r25b25.1.893739314.0.6
r2424.0.821588814.0.1
r23c23.2.856831312.0.9
r22b22.1.717167011.0.5
r21e21.4.70755299.0.9
r21b21.1.63524629.0.8
r20b20.1.59489448.0.7
r19c19.2.53456008.0.2
r18b18.1.50630457.0.2

2.3 結論

根據前一節的兩個表格知道:

opencv 4.8.0 是用 ndk-r18b 編譯, 對應的編譯器是 clang 7.0.2

opencv 4.9.0 是基于 ndk-r25c 編譯, 對應的編譯器是 clang 14.0.7

ndk 沒有使用過 clang 13.0.0 版本, 是從 clang 12.0.9 (ndk-r23c) 直接升級到 clang 14.0.1 (ndk-r24)

編譯選項 -moutline-atomics-mno-outline-atomics 是在 clang 13.0.0 引入的, ndk-r21e 使用的是 clang 9.0.9, 因此會提示“不支持 -mno-outline-atomics 選項”.

3. libgcc.a 的類似報錯: __aarch64_swp4_acq_rel

3.1 問答描述

https://stackoverflow.com/questions/75045297/libgcc-linker-error-hidden-symbol-aarch64-swp1-acq-rel-in-libgcc-a-is-referen (參考鏈接[4]) 給出了 gcc aarch64 下的鏈接報錯, __aarch64_swp4_acq_rel 符號找不到, 這和 opencv issue 24856 報錯很像, 符號名字結尾略有差別。

用戶 Bill Cong 的回答給出了很好的最小復現: 定義和使用 std::atomic<int> 變量, 使用 -O1 優化等級, 在不同編譯器下查看對應的反匯編,

#include <atomic>std::atomic<int> ai(3);int main() {return ai.exchange(5);
}
  • ARM64 gcc 9.3, 不會生成 __aarch64_swp4_acq_rel 匯編指令

  • ARM64 gcc 10.2, 會生成 __aarch64_swp4_acq_rel 匯編指令

  • ARM64 gcc 10.2, 傳入 -mno-outline-atomics 選項, 不會生成 __aarch64_swp4_acq_rel 匯編指令

https://godbolt.org/z/ssK3GGaoE (參考鏈接[5])

在這里插入圖片描述

3.2 分析

-m-outline-atomics 編譯選項是哪個版本引入 GCC 的? 含義是什么?

https://stackoverflow.com/questions/65239845/how-to-enable-mno-outline-atomics-aarch64-flag (參考鏈接[6]) 提到, gcc 9.4 開始提供 -m-outline-atomics 編譯選項。

https://gcc.gnu.org/gcc-9/changes.html (參考鏈接[7]) 則證實了這一點
在這里插入圖片描述

The option -moutline-atomics has been added to aid deployment of the Large System Extensions (LSE) on GNU/Linux systems built with a baseline architecture targeting Armv8-A. When the option is specified code is emitted to detect the presence of LSE instructions at run time and use them for standard atomic operations. For more information please refer to the documentation.

有人在編譯 Android FFmpeg 5.0 后的運行階段遇到報錯 (參考鏈接 [8])

dlopen failed: cannot locate symbol “__aarch64_ldadd8_acq_rel”

參考鏈接[9] 則給出了關于 LSE 的進一步解釋:

Out-of-line Atomics for LSE deploymentAArch64 Large System Extensions (LSE) were introduced in Armv8.1-A. These provide more efficient atomic instructions for large multi-core systems.LLVM 12 adds support for a new flag ‘-moutline-atomics', which detects at runtime whether the processor supports LSE. It then uses these new atomic instructions if possible, falling back to Armv8.0-A LL/SC loops on processors without LSE support. This option behaviour mirrors similar support available within GNU family of projects.  We are working towards making this option enabled by default in the upcoming LLVM13 release.

即:

Armv8.1-A 引入了 LSE(大系統擴展), 用于在多核系統上提供更高效的原子指令。 LLVM12 添加了 -moutline-atomics 編譯選項, 在運行時檢查處理器是否支持 LSE, 如果存在則使用, 不存在則回退到 Arm8.0-A 的 LL/SC。 這個選項在 GNU 家族的工程中也提供了(就是 GCC)。 在 LLVM13 中 -moutline-atomics 選項則被默認開啟。

clang 12.0.1 開始,添加了 -moutline-atomics-mno-outline-atomics 選項(參考鏈接 [10]):
在這里插入圖片描述

而根據參考鏈接 [11], LLVM 的開發者們討論提到, gcc 9.3.1 開始提供了 LSE 的支持, 并在 gcc 10.1 默認開啟:

Outline atomics were added with gcc 9.3.1 and turned on by default in gcc 10.1

3.3 結論

-moutline-atomics 編譯選項表示開啟 LSE (Large System Extension), 意思是在運行時提供更高效率的原子操作, 在 Arm8.1-a 上起作用, 在 Arm8.0 上回退到原本的原子操作處理上。 -mno-outline-atomics 則關閉這一編譯選項。

-moutline-atomics 是在 gcc 9.3.1 版本開始提供, 在 clang 12.0.1 版本開始提供, 但都是默認不開啟狀態。 在 gcc 10.1 版本和 clang 13.0.0-rc1 版本中默認開啟了 -moutline-atomics 編譯選項。

4. __aarch64_ldadd4_acq_rel__aarch64_swp4_acq_rel 指令, 對應的 C/C++ 代碼是什么?

4.1 C++11

基于參考鏈接[5], 很容易構造如下代碼, 并在 armv8-a clang 13.0.0 生成 __aarch64_ldadd4_acq_rel 指令 (仍然使用 -O1):

https://godbolt.org/z/T7vzesfxd (參考鏈接[12])

#include <atomic>
std::atomic<int> ai(3);int main() {ai.fetch_add(1, std::memory_order_acquire);return ai.exchange(5);
}

匯編如下, 生成了 __aarch64_ldadd4_acq__aarch64_swp4_acq_rel 指令.

main:stp     x29, x30, [sp, #-32]!str     x19, [sp, #16]mov     x29, spadrp    x19, aiadd     x19, x19, :lo12:aimov     w0, #1mov     x1, x19bl      __aarch64_ldadd4_acqmov     w0, #5mov     x1, x19bl      __aarch64_swp4_acq_relldr     x19, [sp, #16]ldp     x29, x30, [sp], #32retai:.word   3

4.2 C++03: ncnn XADD 宏的實現

ncnn 庫使用 C++03 編譯, 在大部分平臺使用到了 __atomic_fetch_add, __sync_fetch_add_add 等類似的 builtin 函數:

https://github.com/Tencent/ncnn/blob/20250503/src/allocator.h#L105-L151 (參考鏈接[13])

#if NCNN_THREADS
// exchange-add operation for atomic operations on reference counters
#if defined __riscv && !defined __riscv_atomic
// riscv target without A extension
static NCNN_FORCEINLINE int NCNN_XADD(int* addr, int delta)
{int tmp = *addr;*addr += delta;return tmp;
}
#elif defined __INTEL_COMPILER && !(defined WIN32 || defined _WIN32)
// atomic increment on the linux version of the Intel(tm) compiler
#define NCNN_XADD(addr, delta) (int)_InterlockedExchangeAdd(const_cast<void*>(reinterpret_cast<volatile void*>(addr)), delta)
#elif defined __GNUC__
#if defined __clang__ && __clang_major__ >= 3 && !defined __ANDROID__ && !defined __EMSCRIPTEN__ && !defined(__CUDACC__)
#ifdef __ATOMIC_ACQ_REL
#define NCNN_XADD(addr, delta) __c11_atomic_fetch_add((_Atomic(int)*)(addr), delta, __ATOMIC_ACQ_REL)
#else
#define NCNN_XADD(addr, delta) __atomic_fetch_add((_Atomic(int)*)(addr), delta, 4)
#endif
#else
#if defined __ATOMIC_ACQ_REL && !defined __clang__
// version for gcc >= 4.7
#define NCNN_XADD(addr, delta) (int)__atomic_fetch_add((unsigned*)(addr), (unsigned)(delta), __ATOMIC_ACQ_REL)
#else
#define NCNN_XADD(addr, delta) (int)__sync_fetch_and_add((unsigned*)(addr), (unsigned)(delta))
#endif
#endif
#elif defined _MSC_VER && !defined RC_INVOKED
#define NCNN_XADD(addr, delta) (int)_InterlockedExchangeAdd((long volatile*)addr, delta)
#else

但查看 ncnn 庫文件的反匯編, 例如 ncnn-20250503-android-shared.zip, 并沒有找到 __atomic_fetch_add 指令:

aarch64-linux-android-objdump -d ncnn-20250503-android-shared/arm64-v8a/lib/libncnn.so | ag '__aarch64_ldadd4_acq'

原因是 ncnn 的 CMakeLists.txt 里主動開啟了 -mno-outline-atomics:

https://github.com/Tencent/ncnn/blob/master/src/CMakeLists.txt#L648-L652

    if(ANDROID_NDK_MAJOR AND (ANDROID_NDK_MAJOR GREATER_EQUAL 23))# llvm 12 in ndk-23 enables out-of-line atomics by default# disable this feature for fixing linking atomic builtins issue with old ndktarget_compile_options(ncnn PRIVATE -mno-outline-atomics)endif()

(此處存疑, 可能是 ncnn 注釋 typo, 個人理解是 llvm 13 和 ndk-r25 默認開啟 out-of-line atomics; nihui: 使用 __aarch64_ldadd4_acq_rel后,樹莓派上會 crash,鏈接器會有undefined行為, 因此 ncnn 未開啟 )

4.3 自行構造

構造了簡單直白的一份 MY_XADD 宏的實現: https://godbolt.org/z/x567r5Gfr (參考鏈接[14])

#if _MSC_VER
#   include <windows.h>
#   define MY_XADD(addr, delta) ::InterlockedExchangeAdd((volatile long*)(addr), delta)
#elif __linux__
#   define MY_XADD __sync_fetch_and_add
#endifint main() {int refcount = 1;return MY_XADD(&refcount, -1);
}

使用 -O1 優化等級, 在各個編譯器下結果如下:

在這里插入圖片描述

  • armv8-a clang 12.0.0: 生成 “平凡的” ldaxr, stlxr 指令
  • armv8-a clang 13.0.0: 生成 __aarch64_ldadd4_acq_rel 指令
  • armv8-a clang 13.0.0, 生成 -mno-outline-atomics 編譯選項: 生成 “平凡的” ldaxr, stlxr 指令
  • arm64 msvc v19.43 VS17.13: 生成 “平凡的” ldaxr, stlxr 指令
  • x86-64 gcc 15.1: 生成 lock xadd 指令

ldaxr 指令的解釋:

Load-Acquire Exclusive Register derives an address from a base register value, loads a 32-bit word or 64-bit doubleword from memory, and writes it to a register. The memory access is atomic. The PE marks the physical address being accessed as an exclusive access. This exclusive access mark is checked by Store Exclusive instructions. See Synchronization and semaphores. The instruction also has memory ordering semantics as described in Load-Acquire, Store-Release. For information about memory accesses, see Load/Store addressing modes.

Load-Acquire Exclusive Register 指令根據基址寄存器的值計算地址,從內存中讀取一個 32 位字(word)或 64 位雙字(doubleword),并寫入目標寄存器。此內存訪問是原子的。處理單元(PE)會將正在訪問的物理地址標記為“獨占訪問”,該標記稍后由 Store Exclusive 指令檢查。詳見“同步與信號量”一節。
此外,該指令具有 Load-Acquire/Store-Release 描述的內存排序語義。有關內存訪問的更多信息,請參閱“裝載/存儲尋址模式”。

stlxr 指令的解釋:

Store-Release Exclusive Register stores a 32-bit word or a 64-bit doubleword to memory if the PE has exclusive access to the memory address, from two registers, and returns a status value of 0 if the store was successful, or of 1 if no store was performed. See Synchronization and semaphores. The memory access is atomic. The instruction also has memory ordering semantics as described in Load-Acquire, Store-Release. For information about memory accesses, see Load/Store addressing modes.

Store-Release Exclusive Register(存儲-釋放獨占寄存器)指令在處理元(PE)對某內存地址擁有獨占訪問權限時,可將兩個寄存器中的數據寫入內存:寫入 32 位字或 64 位雙字。如果寫入成功,指令返回狀態值 0;若未執行寫入,則返回狀態值 1。參見“同步與信號量”。

該內存訪問是原子的。此指令還具備與“Load-Acquire / Store-Release”描述一致的內存排序語義。關于內存訪問的詳細說明,請參閱“加載/存儲尋址模式”。

4.4 分析 libbase.a 庫

前一節構造的最小復現代碼,MY_XADD 宏的定義和使用, 對應到文章開頭 libbase.a 基礎庫中的 BASE_XADD 宏實現:

base/atomic.hpp

#if _MSC_VER
#   include <windows.h>
#   define BASE_XADD(addr, delta) ::InterlockedExchangeAdd((volatile long*)(addr), delta)
#elif __linux__
#   define BASE_XADD __sync_fetch_and_add
#endif

base/atomic.hpp 被不同的編譯器處理:

  • ndk-r18: clang 7.0.2, 編譯出 libbase.a

  • ndk-r25c 或更高版本: clang >= 14.0.7, 編譯出 libfoo.so 和 libbar.a

猜測 libapp1.solibapp2.so 不會接觸到 base/atomic.hpp, 并且這兩個 app so 是用 ndk-r24 或更低版本編譯。 這樣一來, libfoo.so 和 libbar.a 的編譯過程產生了非預期的 __aarch64_ldadd4_acq_rel 匯編指令, 下游的集成人員遇到鏈接報錯, 集成人員換到 clang >= 13.0.0 的 ndk 版本, 也就是 ndk >= r25, 就避免了報錯。

另一種改法: 是 libfoo.solibbar.a 的構建過程, 做類似于 ncnn 的配置, 判斷 ndk >= r24 并添加 -mno-outline-atomics 編譯選項。

5. 總結

gcc 9.3.1 和 clang 12.0.1 添加了 -moutline-atomics 編譯選項, 用來開啟 LSE (Large System Extension), 用于在 Armv8.1-a 上改善多核情況下的原子操作的性能。

這個選項在 gcc 9 和 clang 12 是默認不開啟的, 相當于是默認開啟了 -mno-outline-atomics

從 gcc 10 和 clang 13 開始默認開啟 -moutline-atomics 編譯選項。

ndk 版本和 clang 版本有對應的關系, clang >= 13 對應到 ndk >= r24。

當使用 clang >= 13 (ndk >= r24) 編譯了帶有 __sync_fetch_and_add (C/C++ Builtin) 或 C++11 的 std::atomic<T> 的代碼, 例如 opencv/ncnn 中的 XADD 的實現, 會生成 __aarch64_ldadd4_acq_rel 等 LSE 相關的匯編指令, 這樣的二進制被 clang < 13 (ndk < r24) 的編譯器做鏈接, 會遇到 __aarch64_ldadd4_acq_rel 符號找不到的問題。

當遇到上述報錯, 可以對齊編譯器版本到 clang >= 13 (ndk >= r24), 或手動指定 -mno-outline-atomics 選項。

如果是 clang 12 或 gcc 9 編譯器, 但傳入了 -moutline-atomics 選項, 也會發生類似的鏈接報錯, 處理方式同前。

當然, 考慮到 ndk-r24 沒有 ndk-24b, ndk-r24c 等版本, 建議用 ndk >= r25c 的版本。

References

  • [1] https://github.com/opencv/opencv/issues/24856
  • [2] https://github.com/llvm/llvm-project/commit/c5e7e649d537067dec7111f3de1430d0fc8a4d11
  • [3] https://stackoverflow.com/questions/53385892/find-the-ndk-version-used-for-building-opencv-android-native-libraries
  • [4] https://stackoverflow.com/questions/75045297/libgcc-linker-error-hidden-symbol-aarch64-swp1-acq-rel-in-libgcc-a-is-referen
  • [5] https://godbolt.org/z/ssK3GGaoE
  • [6] https://stackoverflow.com/questions/65239845/how-to-enable-mno-outline-atomics-aarch64-flag
  • [7] https://gcc.gnu.org/gcc-9/changes.html
  • [8] https://juejin.cn/post/7149468268674154510
  • [9] https://community.arm.com/arm-community-blogs/b/tools-software-ides-blog/posts/llvm12-for-arm
  • [10] https://releases.llvm.org/12.0.1/tools/clang/docs/ReleaseNotes.html
  • [11] https://reviews.llvm.org/D93585
  • [12] https://godbolt.org/z/T7vzesfxd
  • [13] https://github.com/Tencent/ncnn/blob/20250503/src/allocator.h#L105-L151
  • [14] https://godbolt.org/z/x567r5Gfr

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/diannao/82640.shtml
繁體地址,請注明出處:http://hk.pswp.cn/diannao/82640.shtml
英文地址,請注明出處:http://en.pswp.cn/diannao/82640.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

如何清除windows 遠程桌面連接的IP記錄

問題 在遠程桌面連接后&#xff0c;會在輸入列表留下歷史IP記錄&#xff0c;無用的IP多了會影響我們查找效率&#xff0c;也不安全。 現介紹如何手動刪除這些IP記錄。 解決方案 1、打開注冊表 按 Win R&#xff0c;輸入 regedit&#xff0c;回車定位到遠程桌面記錄的注冊表…

使用 React Native實現鴻蒙開發的詳細方案

一、環境準備 1. 基礎環境要求 操作系統:Windows 10/11 或 macOS (建議版本最新)Node.js: v16.x 或更高版本npm: v8.x 或更高版本Java JDK: 11 或更高版本DevEco Studio: 3.1 或更高版本 (鴻蒙官方IDE)2. 安裝 DevEco Studio 從華為開發者官網下載安裝時選擇以下組件: Harmo…

貪心算法應用:頂點覆蓋問題詳解

貪心算法應用&#xff1a;頂點覆蓋問題詳解 貪心算法是解決頂點覆蓋問題的經典方法之一。下面我將從基礎概念到高級優化&#xff0c;全面詳細地講解頂點覆蓋問題及其貪心算法解決方案。 一、頂點覆蓋問題基礎 1. 問題定義 頂點覆蓋問題&#xff08;Vertex Cover Problem&am…

Excel安全防護:開源批量加密工具推薦與使用指南

先放下載鏈接&#xff1a;https://tool.nineya.com/s/1iqsn2sh0 在日常辦公里&#xff0c;像財務數據、客戶信息、項目報表這類核心資料&#xff0c;常常是以 Excel 文件的形式來存儲的。要是手動一個一個地給這些文件加密&#xff0c;那可太費時間和精力了&#xff0c;而且還…

【C++】學習、項目時Debug總結

這里寫目錄標題 1. 內存問題1.1. 內存泄漏1.1.1. 內存泄漏案例檢查方法1.1.2. 主線程提前退出導致【控】1.1.3. PostThreadMessage失敗導致的內存泄漏**【控】**1.1.4. SendMessage 時關閉客戶端【控】1.1.5. 線程機制導致【**控】**1.1.6. exit&#xff08;0&#xff09;導致【…

2025 后端自學UNIAPP【項目實戰:旅游項目】1、創建項目框架

1、創建項目 ①項目名稱&#xff1a;自定義&#xff0c;【我是travel】 ②vue版本&#xff1a;vue3 ③其他默認&#xff0c;最后創建 2、創建頁面 ①展開自己剛才創建的項目 ②單擊選中pages文件夾 --->鼠標右鍵---->新建頁面 ③頁面名稱&#xff1a;自定義favouri…

WPF 子界面修改后通知到主頁面

子頁面&#xff1a; public partial class MyPopupWindow : Window { public event Action OnClose; private void CloseWindowButton_Click(object sender, RoutedEventArgs e) { OnClose?.Invoke(); this.Close(); } } 主界面&#xff1a…

Python中的標識、相等性與別名:深入理解對象引用機制

在Python編程中&#xff0c;理解變量如何引用對象以及對象之間的比較方式是至關重要的基礎概念。本文將通過Lewis Carroll的筆名示例&#xff0c;深入探討Python中的對象標識、相等性判斷以及別名機制。 別名現象&#xff1a;變量共享同一對象 >>> charles {name: …

python 閉包獲取循環數據經典 bug

問題代碼 def create_functions():functions []for i in range(3):# 創建一個函數,期望捕獲當前循環的i值functions.append(lambda: print(f"My value is: {i}"))return functions# 創建三個函數 f0, f1, f2 create_functions()# 調用這些函數 f0() # 期望輸出 &…

克里金模型+多目標優化+多屬性決策!Kriging+NSGAII+熵權TOPSIS!

目錄 效果一覽基本介紹程序設計參考資料 效果一覽 基本介紹 克里金模型多目標優化多屬性決策&#xff01;KrigingNSGAII熵權TOPSIS&#xff01;&#xff01;matlab2023b語言運行&#xff01; 1.克里金模型&#xff08;Kriging Model&#xff09;是一種基于空間統計學的插值方法…

Prompt Engineering 提示詞工程學習

一、Prompt Engineering 簡介 Prompt Engineering 是設計和優化輸入提示(Prompt)以獲得預期輸出的過程。在與大型語言模型(如 GPT-4)交互時,如何構造提示會顯著影響模型的回答質量。 二、Prompt 的重要性 提高生成準確性:通過正確的 Prompt 引導,模型能夠更好地理解用…

MATLAB安裝常見問題及解決方案詳解(含代碼示例)

MATLAB作為科學計算和工程分析的核心工具&#xff0c;其安裝過程可能因操作系統版本、硬件配置或網絡環境等因素而出現各種問題。本文基于MATLAB官方文檔和社區經驗&#xff0c;系統總結了安裝過程中常見的問題&#xff0c;并提供詳細的解決方案和代碼示例&#xff0c;幫助用戶…

免安裝 + 快速響應Photoshop CS6 精簡版低配置電腦修圖

各位PS小白和修圖大神們&#xff0c;今天來給大家聊聊Photoshop CS6精簡版這個寶藏軟件&#xff01; Photoshop CS6精簡版就是Adobe Photoshop CS6的“瘦身版”&#xff0c;它把一些不常用的功能給簡化了&#xff0c;只留下核心工具&#xff0c;特別適合那些想高效操作、節省系…

微服務架構實戰:從服務拆分到RestTemplate遠程調用

微服務架構實戰&#xff1a;從服務拆分到RestTemplate遠程調用 一 . 服務拆分1.1 服務拆分注意事項1.2 導入服務拆分 Demo1.3 小結 二 . 服務間調用2.1 注冊 RestTemplate2.2 實現遠程調用2.3 小結 三 . 提供方和消費方 在分布式系統設計中&#xff0c;微服務架構因其靈活性、可…

MySQL 索引與事務詳解

目錄 一、索引&#xff08;Index&#xff09; 二、事務&#xff08;Transaction&#xff09; 三、總結 一、索引&#xff08;Index&#xff09; 索引的本質&#xff1a;一種數據結構&#xff08;如 BTree、Hash&#xff09;&#xff0c;用于快速定位數據&#xff0c;避免全…

macOS Python 環境配置指南

1. 檢查現有 Python 環境 python3 --version # 檢查 Python 3 版本 pip3 --version # 檢查 pip 版本 2. 安裝 pyenv&#xff08;Python 版本管理工具&#xff09; # 使用 Homebrew 安裝 pyenvbrew install pyenv# 配置 pyenv 環境變量&#xff08;添加到 ~/.zshrc&#…

游戲引擎學習第272天:顯式移動轉換

回顧并為今天的內容鋪墊背景 我們剛開始為游戲主角編寫一些程序邏輯&#xff0c;因為我們之前已經完成了大部分引擎方面的開發&#xff0c;現在可以專注在角色身上。這個角色的移動方式會有些特別&#xff0c;與大多數游戲角色的運動機制不太一樣。我們當前正在實現的控制方式…

軟件測試都有什么???

文章目錄 一、白盒測試&#xff08;結構測試&#xff09;二、黑盒測試&#xff08;功能測試&#xff09;三、灰盒測試四、其他測試類型五、覆蓋準則對比六、應用場景 軟件測試主要根據測試目標、技術手段和覆蓋準則進行分類。分為白盒測試、黑盒測試、灰盒測試及其他補充類型 一…

very_easy_sql(SSRF+SQL注入)

題目有一行提示&#xff1a; you are not an inner user, so we can not let you have identify~&#xff08;你不是內部用戶&#xff0c;所以我們不能讓你進行身份驗證&#xff09;聯想到可能存在SSRF漏洞&#xff0c;一般情況下&#xff0c;SSRF攻擊的目標是外網無法訪問的內…

國內外主流AI編程工具全方位對比分析(截至2025年5月)

一、國際主流工具對比 1. Windsurf&#xff08;Codeium公司&#xff09; 核心功能&#xff1a;代理型AI編程&#xff08;代碼導航/修改/命令執行&#xff09;、瀏覽器DOM訪問、網頁研究功能語言支持&#xff1a;70語言&#xff0c;包括Python/Java/JavaScript/Rust等[[22-23]…