Birleştirme
- C++ kursu
- Uzman
- Ders 47/47
- 6 dk
Tüm uzman konularını birleştirerek çalışan bir mini uygulama yazarsın.
extern "C" ile C-uyumlu arayüz
C++ derleyicisi fonksiyon adlarına name mangling uygular (örneğin engine_report, _Z13engine_reportv olur). Bu, aşırı yükleme (overloading) için gerekli olsa da C'den veya başka dillerden çağırmayı zorlaştırır. extern "C" bildirimi mangling işlemini kapatır.
Bu son derste tüm uzman konularını birleştireceğiz: Factorial<5>::value (TMP), Engine::parallelSum() (atomic), sahte kayıt erişimi (volatile) ve extern "C" arayüz (ABI). Sonuç, C'den de çağrılabilen tek bir rapor fonksiyonu olacak.
Tüm parçaları birleştirme
Son adımda tüm parçaları bir extern "C" fonksiyonunda birleştiririz. Bu fonksiyon C'den de çağrılabilir; çünkü adına mangling uygulanmaz. İçinde derleme zamanı faktöriyel ve paralel toplamı birlikte kullanırız.
Örnek: extern "C" int engine_report() { return Factorial<5>::value + Engine::parallelSum(); }. Bu fonksiyon 120 + 36 = 156 döndürür. main içinden std::cout << engine_report(); ile çağırırız. Böylece tüm uzman konuları tek bir ABI arayüzünde birleşir.
Uygulama extern "C" engine_report fonksiyonunu ekle
Önceki dersin çözümünü al. Factorial şablonundan sonra extern "C" int engine_report() fonksiyonunu ekle. Gövdesi return Factorial<5>::value + Engine::parallelSum(); olsun. main içinde kayıt erişim çıktısından sonra std::cout << engine_report(); ekle.
Başlangıç kodu
#include <iostream>
#include <atomic>
#include <thread>
#include <cstdint>
class Engine {
public:
static const int Version = 1;
static int parallelSum() {
std::atomic<int> total{0};
std::thread t1([&]() { for (int i = 1; i <= 4; ++i) total += i; });
std::thread t2([&]() { for (int i = 5; i <= 8; ++i) total += i; });
t1.join();
t2.join();
return total.load();
}
static std::uint32_t readRegister(volatile std::uint32_t* reg) {
return *reg;
}
static void writeRegister(volatile std::uint32_t* reg, std::uint32_t value) {
*reg = value;
}
};
template <int N>
struct Factorial {
static const int value = N * Factorial<N - 1>::value;
};
template <>
struct Factorial<0> {
static const int value = 1;
};
// C-uyumlu rapor fonksiyonunu buraya ekle
int main() {
std::cout << "Hazır" << std::endl;
std::cout << Factorial<5>::value << std::endl;
std::cout << Engine::parallelSum() << std::endl;
volatile std::uint32_t reg = 0;
Engine::writeRegister(®, 64);
std::cout << Engine::readRegister(®) << std::endl;
// engine_report çağrısını ekle
return 0;
}Örnek çözüm
#include <iostream>
#include <atomic>
#include <thread>
#include <cstdint>
class Engine {
public:
static const int Version = 1;
static int parallelSum() {
std::atomic<int> total{0};
std::thread t1([&]() { for (int i = 1; i <= 4; ++i) total += i; });
std::thread t2([&]() { for (int i = 5; i <= 8; ++i) total += i; });
t1.join();
t2.join();
return total.load();
}
static std::uint32_t readRegister(volatile std::uint32_t* reg) {
return *reg;
}
static void writeRegister(volatile std::uint32_t* reg, std::uint32_t value) {
*reg = value;
}
};
template <int N>
struct Factorial {
static const int value = N * Factorial<N - 1>::value;
};
template <>
struct Factorial<0> {
static const int value = 1;
};
extern "C" int engine_report() {
return Factorial<5>::value + Engine::parallelSum();
}
int main() {
std::cout << "Hazır" << std::endl;
std::cout << Factorial<5>::value << std::endl;
std::cout << Engine::parallelSum() << std::endl;
volatile std::uint32_t reg = 0;
Engine::writeRegister(®, 64);
std::cout << Engine::readRegister(®) << std::endl;
std::cout << engine_report();
return 0;
}Beklenen çıktı
Hazır 120 36 64 156
Soru ve cevaplar
Dersin sorularını cevaplarıyla birlikte inceleyebilirsin. Kendini denemek istersen dersi interaktif olarak çöz.
1 extern "C" ne yapar?
extern "C" int engine_report();- İsim gizler
- İşletim sistemini değiştirir
- Name mangling'i kapatır Doğru cevap
- Çalışma zamanı denetimini artırır
Açıklama: extern "C" fonksiyon adına mangling uygulanmasını engeller.
2 Parçayı rolüne eşle
| Kavram | Anlamı |
|---|---|
extern "C" |
C-uyumlu arayüz |
Factorial<5>::value |
Derleme zamanı sabiti |
std::atomic<int> |
Paralel güvenli sayaç |
volatile |
Donanım kaydı erişimi |
3 extern "C" bildirimini tamamla
extern "C" ____ engine_report() { return Factorial<5>::value + Engine::parallelSum(); }
extern "C" int engine_report() { return Factorial<5>::value + Engine::parallelSum(); }
Açıklama: Dönüş türü int; sayı döndürür.