<string> cin与getline区别(version 1)

本文深入探讨了C++中cin和getline函数的使用方法及其区别,特别是在处理包含空格的字符串输入时的行为。通过具体示例展示了如何利用这两种输入方式来分别捕获单词和整行文本,并解释了它们在遇到空白字符时的不同处理机制。
string idol, boy;
cin>>idol;
getline(cin,boy);
cout << "idol is " << idol << endl
     << "boy is " << boy << endl;

若第一次输入的字符中包括空格,空格之后的内容会舍去或者输入到下一个变量中。

以上若输入“if you can try”,当按enter之后,程序即输出结果,输出结果为:

idol is if
boy is you can try

若调换输入的顺序:

string idol, boy;
getline(cin,boy);
cin>>idol;
cout << "idol is " << idol << endl
     << "boy is " << boy << endl;

以上输入“if you can try”并按回车键之后,程序会要求输入另一个字符,若为“you would find”,结果会是:

idol is you
boy is if you can try

 

// 轻量化杀毒软件 - 终极整合版 v9.0 #define _CRT_SECURE_NO_WARNINGS #include <windows.h> #include <iostream> #include <fstream> #include <string> #include <vector> #include <set> #include <map> #include <thread> #include <mutex> #include <sstream> #include <algorithm> #include <tlhelp32.h> using namespace std; // ========== 动态加载 Psapi.dll ========== typedef BOOL (WINAPI *LPFN_GETMODULEFILENAMEEXA)( HANDLE hProcess, HMODULE hModule, LPSTR lpFilename, DWORD nSize ); HMODULE hPsapi = nullptr; LPFN_GETMODULEFILENAMEEXA pGetModuleFileNameExA = nullptr; BOOL SafeGetModuleFileNameExA(HANDLE hProcess, HMODULE hModule, LPSTR lpFilename, DWORD nSize) { if (pGetModuleFileNameExA) return pGetModuleFileNameExA(hProcess, hModule, lpFilename, nSize); strcpy(lpFilename, "<unknown>"); return FALSE; } bool LoadPsapiFunction() { hPsapi = LoadLibraryA("Psapi.dll"); if (!hPsapi) return false; pGetModuleFileNameExA = (LPFN_GETMODULEFILENAMEEXA)GetProcAddress(hPsapi, "GetModuleFileNameExA"); return pGetModuleFileNameExA != nullptr; } // ========== 全局常量 ========== const string LOG_FILE = "antivirus.log"; const string WHITELIST_FILE = "whitelist.txt"; const string QUARANTINE_DIR = "quarantine"; const string QUARANTINE_LOG = "quarantine_log.txt"; map<string, string> g_whitelist; // 文件/目录白名单 set<string> g_trustedProcesses; // 可信进程名(防误报) volatile bool g_monitoring = false; int fileCount = 0, suspiciousCount = 0; mutex printMutex; // ========== 函数前置声明 ========== void log(const string& msg); string toLower(string s); string normalizePath(const string& path); void loadWhitelist(); void saveWhitelist(); bool isWhitelisted(const string& filePath); bool isTrustedProcess(const string& exeName); bool SuspendProcess(DWORD pid); bool ResumeProcess(DWORD pid); enum Action { TERMINATE, IGNORE, ADD_TO_WHITELIST }; Action ShowDecisionDialog(const string& processName, const string& reason); DWORD WINAPI BehaviorMonitorThread(LPVOID param); void addFalsePositive(); void manageQuarantine(); bool restoreFileFromQuarantine(const string& quarantinedFile); void deleteFileFromQuarantine(const string& quarantinedFile); void clearQuarantine(); vector<string> listQuarantinedFiles(); void quarantineFile(const string& filePath); bool isFileSuspicious(const string& filePath, string& matchedRule); void handleSuspiciousFile(const string& filePath); void scanPath(const string& root); void scanCurrentDir(); void scanCustomDir(); void scanAllDrives(); void startRealTimeMonitor(); void stopRealTimeMonitor(); void showMainMenu(); // ========== 工具函数 ========== void log(const string& msg) { ofstream out(LOG_FILE.c_str(), ios::app); if (!out.is_open()) return; time_t t = time(0); char* ts = ctime(&t); if (ts) ts[strlen(ts)-1] = 0; out << "[" << ts << "] " << msg << endl; out.close(); } string toLower(string s) { transform(s.begin(), s.end(), s.begin(), ::tolower); return s; } string normalizePath(const string& path) { if (path.empty()) return ""; string norm = path; replace(norm.begin(), norm.end(), '/', '\\'); transform(norm.begin(), norm.end(), norm.begin(), ::tolower); DWORD attr = GetFileAttributesA(norm.c_str()); if (attr != 0xFFFFFFFF && (attr & FILE_ATTRIBUTE_DIRECTORY)) { if (!norm.empty() && norm.back() != '\\') norm += '\\'; } return norm; } // ========== 白名单操作 ========== void loadWhitelist() { ifstream in(WHITELIST_FILE.c_str()); if (!in.is_open()) { ofstream create(WHITELIST_FILE.c_str()); create.close(); cout << "✅ 白名单文件不存在,已创建。\n"; return; } string line; while (getline(in, line)) { size_t pos = line.find('|'); if (pos != string::npos) { string path = normalizePath(line.substr(0, pos)); string type = line.substr(pos + 1); if (type == "FILE" || type == "DIR") g_whitelist[path] = type; } else { g_trustedProcesses.insert(toLower(line)); // 信任的进程名 } } in.close(); cout << "✅ 已加载 " << g_whitelist.size() << " 个路径白名单," << g_trustedProcesses.size() << " 个可信进程。\n"; log("Loaded whitelist."); } void saveWhitelist() { ofstream out(WHITELIST_FILE.c_str()); if (!out.is_open()) return; for (const auto& item : g_whitelist) out << item.first << "|" << item.second << endl; for (const string& proc : g_trustedProcesses) out << proc << endl; out.close(); log("Whitelist saved."); } bool isWhitelisted(const string& filePath) { string np = normalizePath(filePath); if (g_whitelist.find(np) != g_whitelist.end()) return true; for (const auto& item : g_whitelist) if (item.second == "DIR" && np.find(item.first) == 0) return true; return false; } bool isTrustedProcess(const string& exeName) { return g_trustedProcesses.find(toLower(exeName)) != g_trustedProcesses.end(); } // ========== 挂起/恢复进程(使用 NtSuspendProcess)========== using NtSuspendProcess = NTSTATUS(NTAPI*)(HANDLE ProcessHandle); using NtResumeProcess = NTSTATUS(NTAPI*)(HANDLE ProcessHandle); bool SuspendProcess(DWORD pid) { HANDLE hProc = OpenProcess(PROCESS_SUSPEND_RESUME, FALSE, pid); if (!hProc) return false; NtSuspendProcess pNtSuspendProcess = (NtSuspendProcess)GetProcAddress(GetModuleHandleA("ntdll.dll"), "NtSuspendProcess"); if (pNtSuspendProcess) { pNtSuspendProcess(hProc); CloseHandle(hProc); return true; } CloseHandle(hProc); return false; } bool ResumeProcess(DWORD pid) { HANDLE hProc = OpenProcess(PROCESS_SUSPEND_RESUME, FALSE, pid); if (!hProc) return false; NtResumeProcess pNtResumeProcess = (NtResumeProcess)GetProcAddress(GetModuleHandleA("ntdll.dll"), "NtResumeProcess"); if (pNtResumeProcess) { pNtResumeProcess(hProc); CloseHandle(hProc); return true; } CloseHandle(hProc); return false; } // ========== 用户决策弹窗 ========== Action ShowDecisionDialog(const string& processName, const string& reason) { stringstream msg; msg << "发现可疑行为!\n\n" << "进程: " << processName << "\n" << "原因: " << reason << "\n\n" << "请选择处理方式:\n" << "是 —— 终止该进程\n" << "否 —— 忽略本次\n" << "取消 —— 加入白名单并忽略"; int result = MessageBoxA(nullptr, msg.str().c_str(), "【安全警告】", MB_YESNOCANCEL | MB_ICONWARNING); switch (result) { case IDYES: return TERMINATE; case IDNO: return IGNORE; default: return ADD_TO_WHITELIST; } } // ========== 行为监控线程 ========== DWORD WINAPI BehaviorMonitorThread(LPVOID param) { cout << "🔍 启动行为监控引擎...\n"; log("Behavior monitor started"); set<DWORD> prevPids; set<string> prevAutoRun; while (g_monitoring) { Sleep(2000); // --- 1. 监控新进程 --- HANDLE hSnap = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0); if (hSnap == INVALID_HANDLE_VALUE) continue; PROCESSENTRY32 pe = {sizeof(pe)}; set<DWORD> currPids; if (Process32First(hSnap, &pe)) { do { currPids.insert(pe.th32ProcessID); if (prevPids.find(pe.th32ProcessID) == prevPids.end()) { string exeName = toLower(pe.szExeFile); if (isTrustedProcess(exeName)) continue; HANDLE hProc = OpenProcess(PROCESS_QUERY_LIMITED_INFORMATION, FALSE, pe.th32ProcessID); if (!hProc) continue; char path[MAX_PATH] = {0}; if (SafeGetModuleFileNameExA(hProc, nullptr, path, MAX_PATH)) { string lowerPath = toLower(path); if (lowerPath.find("\\temp\\") != string::npos || lowerPath.find("downloads") != string::npos || lowerPath.find("appdata\\local\\temp") != string::npos) { SuspendProcess(pe.th32ProcessID); MessageBoxA(nullptr, ("⏸️ 已暂停可疑进程:\n" + string(pe.szExeFile)).c_str(), "进程已暂停", MB_OK | MB_ICONINFORMATION); Action act = ShowDecisionDialog(pe.szExeFile, "从临时目录启动"); if (act == TERMINATE) { TerminateProcess(hProc, 0); log("Terminated suspicious process: " + string(pe.szExeFile)); } else if (act == ADD_TO_WHITELIST) { g_trustedProcesses.insert(exeName); saveWhitelist(); ResumeProcess(pe.th32ProcessID); MessageBoxA(nullptr, ("✅ 已将 " + string(pe.szExeFile) + " 加入白名单").c_str(), "已信任", MB_OK); log("Added to whitelist: " + string(pe.szExeFile)); } else { ResumeProcess(pe.th32ProcessID); } } } CloseHandle(hProc); } } while (Process32Next(hSnap, &pe)); } CloseHandle(hSnap); prevPids = currPids; // --- 2. 监控自启动项 --- HKEY hKey; if (RegOpenKeyEx(HKEY_CURRENT_USER, "Software\\Microsoft\\Windows\\CurrentVersion\\Run", 0, KEY_READ, &hKey) == ERROR_SUCCESS) { set<string> currAutoRun; char name[256], path[1024]; DWORD i = 0, nameLen, pathLen, type; while (true) { nameLen = sizeof(name); pathLen = sizeof(path); LONG ret = RegEnumValue(hKey, i++, name, &nameLen, nullptr, &type, (BYTE*)path, &pathLen); if (ret != ERROR_SUCCESS) break; currAutoRun.insert(string(name)); if (prevAutoRun.find(name) == prevAutoRun.end()) { string p = toLower(path); if (p.find(".exe") != string::npos && p.find("chrome") == string::npos && p.find("steam") == string::npos) { Action act = ShowDecisionDialog("autorun:" + string(name), "新增可疑自启动项"); if (act == TERMINATE) { RegDeleteValue(hKey, name); MessageBoxA(nullptr, "已删除注册表自启动项", "✅ 删除成功", MB_OK); log("Deleted autorun: " + string(name)); } else if (act == ADD_TO_WHITELIST) { g_trustedProcesses.insert("autorun:" + toLower(name)); saveWhitelist(); } } } } RegCloseKey(hKey); prevAutoRun = currAutoRun; } // --- 3. 检测远程线程注入 --- HANDLE hThreadSnap = CreateToolhelp32Snapshot(TH32CS_SNAPTHREAD, 0); if (hThreadSnap != INVALID_HANDLE_VALUE) { THREADENTRY32 te = {sizeof(te)}; if (Thread32First(hThreadSnap, &te)) { do { HANDLE hThread = OpenThread(THREAD_GET_CONTEXT, FALSE, te.th32ThreadID); if (hThread) { DWORD ownerPid = te.th32OwnerProcessID; char ownerName[MAX_PATH] = {0}; HANDLE hProc = OpenProcess(PROCESS_QUERY_LIMITED_INFORMATION, FALSE, ownerPid); if (hProc && SafeGetModuleFileNameExA(hProc, nullptr, ownerName, MAX_PATH)) { string owner = toLower(ownerName); if (owner.find("explorer.exe") != string::npos || owner.find("winlogon.exe") != string::npos || owner.find("lsass.exe") != string::npos) { SuspendProcess(ownerPid); MessageBoxA(nullptr, ("⏸️ 检测到向关键进程注入代码: " + string(ownerName)).c_str(), "⚠️ DLL 注入警告", MB_OK | MB_ICONERROR); Action act = ShowDecisionDialog(ownerName, "DLL 注入"); if (act == TERMINATE) { TerminateProcess(hProc, 0); log("💥 Terminated injected process: " + string(ownerName)); } else if (act == ADD_TO_WHITELIST) { g_trustedProcesses.insert(owner); saveWhitelist(); ResumeProcess(ownerPid); } else { ResumeProcess(ownerPid); } } } if (hProc) CloseHandle(hProc); CloseHandle(hThread); } } while (Thread32Next(hThreadSnap, &te)); } CloseHandle(hThreadSnap); } } return 0; } // ========== 隔离区管理 ========== vector<string> listQuarantinedFiles() { vector<string> files; WIN32_FIND_DATAA data; string pattern = QUARANTINE_DIR + "\\*"; HANDLE hFind = FindFirstFileA(pattern.c_str(), &data); if (hFind == INVALID_HANDLE_VALUE) return files; do { if (!(data.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY)) files.push_back(string(data.cFileName)); } while (FindNextFileA(hFind, &data)); FindClose(hFind); return files; } bool restoreFileFromQuarantine(const string& quarantinedFile) { string basename = quarantinedFile.substr(quarantinedFile.find_last_of("\\/") + 1); ifstream logIn(QUARANTINE_LOG.c_str()); if (!logIn.is_open()) { cout << "❌ 隔离日志无法打开。\n"; return false; } string line, originalPath; vector<string> remainingLogs; bool found = false; while (getline(logIn, line)) { size_t pos = line.find('='); if (pos != string::npos && line.substr(0, pos) == basename) { originalPath = line.substr(pos + 1); found = true; } else { remainingLogs.push_back(line); } } logIn.close(); if (!found) { cout << "❌ 无法找到该文件的原始路径记录。\n"; return false; } string parentDir = originalPath.substr(0, originalPath.find_last_of("\\/")); DWORD attr = GetFileAttributesA(parentDir.c_str()); if (attr == 0xFFFFFFFF || !(attr & FILE_ATTRIBUTE_DIRECTORY)) { cout << "❌ 原目录不存在:" << parentDir << "\n"; cout << "1. 选择新目录恢复\n2. 取消\n>"; char c; cin >> c; cin.ignore(); if (c != '1') return false; cout << "请输入目标目录: "; string targetDir; getline(cin, targetDir); attr = GetFileAttributesA(targetDir.c_str()); if (attr == 0xFFFFFFFF || !(attr & FILE_ATTRIBUTE_DIRECTORY)) { cout << "❌ 目标目录无效。\n"; return false; } originalPath = targetDir + "\\" + basename; } if (MoveFileA(quarantinedFile.c_str(), originalPath.c_str())) { ofstream logOut(QUARANTINE_LOG.c_str()); for (const string& l : remainingLogs) logOut << l << endl; logOut.close(); cout << "✅ 文件已恢复至: " << originalPath << endl; log("Restored from quarantine: " + originalPath); return true; } else { cout << "❌ 恢复失败,错误码: " << GetLastError() << endl; return false; } } void deleteFileFromQuarantine(const string& quarantinedFile) { string basename = quarantinedFile.substr(quarantinedFile.find_last_of("\\/") + 1); ifstream in(QUARANTINE_LOG.c_str()); vector<string> lines; string line; while (getline(in, line)) { if (line.find("=") != string::npos && line.substr(0, line.find('=')) != basename) { lines.push_back(line); } } in.close(); ofstream out(QUARANTINE_LOG.c_str()); for (const string& l : lines) out << l << endl; out.close(); if (DeleteFileA(quarantinedFile.c_str())) { cout << "🗑️ 文件已永久删除。\n"; log("Deleted from quarantine: " + basename); } else { cout << "❌ 删除失败,错误码: " << GetLastError() << endl; } } void clearQuarantine() { vector<string> files = listQuarantinedFiles(); for (const string& f : files) DeleteFileA((QUARANTINE_DIR + "\\" + f).c_str()); ofstream(QUARANTINE_LOG.c_str()).close(); cout << "🧹 隔离区日志已全部清空。\n"; log("Quarantine cleared."); } void manageQuarantine() { while (true) { vector<string> files = listQuarantinedFiles(); if (files.empty()) { cout << "\n📭 隔离区为空。\n"; break; } cout << "\n--- 🔒 隔离区文件列表 ---\n"; for (size_t i = 0; i < files.size(); ++i) cout << i + 1 << ". " << files[i] << endl; cout << "\n操作选项:\n"; cout << "1. 恢复文件\n2. 删除文件\n3. 清空隔离区\n0. 返回\n>"; char c; cin >> c; cin.ignore(); switch (c) { case '1': { cout << "选择编号: "; int n; cin >> n; cin.ignore(); if (n >= 1 && n <= (int)files.size()) restoreFileFromQuarantine(QUARANTINE_DIR + "\\" + files[n-1]); else cout << "❌ 无效编号。\n"; break; } case '2': { cout << "选择编号: "; int n; cin >> n; cin.ignore(); if (n >= 1 && n <= (int)files.size()) deleteFileFromQuarantine(QUARANTINE_DIR + "\\" + files[n-1]); else cout << "❌ 无效编号。\n"; break; } case '3': clearQuarantine(); break; case '0': return; default: cout << "❌ 无效选择。\n"; } } } void quarantineFile(const string& filePath) { if (!CreateDirectoryA(QUARANTINE_DIR.c_str(), nullptr)) { if (GetLastError() != ERROR_ALREADY_EXISTS) { cout << "❌ 无法创建隔离目录。\n"; return; } } string filename = filePath.substr(filePath.find_last_of("\\/") + 1); string dest = QUARANTINE_DIR + "\\" + filename; string temp = dest; int counter = 1; while (GetFileAttributesA(temp.c_str()) != 0xFFFFFFFF) temp = QUARANTINE_DIR + "\\" + to_string(counter++) + "_" + filename; if (MoveFileA(filePath.c_str(), temp.c_str())) { ofstream logOut(QUARANTINE_LOG.c_str(), ios::app); logOut << temp.substr(temp.find_last_of("\\/") + 1) << "=" << filePath << endl; logOut.close(); cout << "🔒 文件已隔离: " << temp << " (原路径: " << filePath << ")" << endl; log("Quarantined: " + filePath); } else { cout << "❌ 隔离失败!错误码: " << GetLastError() << endl; } } bool isFileSuspicious(const string& filePath, string& matchedRule) { ifstream file(filePath, ios::binary); if (!file.is_open()) return false; string line; vector<pair<string, string>> keywords = { {"format ", "检测到磁盘格式化命令"}, {"del ", "检测到批量删除文件命令"}, {"rd /s", "检测到递归删除目录命令"}, {"shutdown", "检测到关机指令"}, {"reg delete", "检测到注册表删除操作"}, {"powershell -c", "检测到远程代码执行"}, {"wscript.shell", "检测到脚本执行环境创建"}, {"%0|%0", "无限递归自调用"}, {"taskkill /f /im", "终止关键系统程序"} }; while (getline(file, line)) { transform(line.begin(), line.end(), line.begin(), ::tolower); for (const auto& kw : keywords) { if (line.find(kw.first) != string::npos) { matchedRule = kw.second; file.close(); return true; } } } file.close(); return false; } void handleSuspiciousFile(const string& filePath) { string matchedRule; if (!isFileSuspicious(filePath, matchedRule)) return; stringstream msg; msg << "发现可疑脚本!\n\n" << "文件路径: " << filePath << "\n" << "威胁类型: " << matchedRule << "\n\n" << "处理方式:\n" << "是 —— 隔离该文件\n" << "否 —— 加入白名单\n" << "取消 —— 忽略本次"; MessageBeep(MB_ICONEXCLAMATION); int result = MessageBoxA(nullptr, msg.str().c_str(), "【安全警告】", MB_YESNOCANCEL | MB_ICONWARNING); switch (result) { case IDYES: quarantineFile(filePath); break; case IDNO: g_whitelist[normalizePath(filePath)] = "FILE"; saveWhitelist(); MessageBoxA(nullptr, ("已信任: " + filePath).c_str(), "✅ 已加入白名单", MB_OK); break; case IDCANCEL: break; } } void scanPath(const string& root) { WIN32_FIND_DATAA data; string pattern = root + "\\*"; HANDLE hFind = FindFirstFileA(pattern.c_str(), &data); if (hFind == INVALID_HANDLE_VALUE) { cout << "❌ 无法访问: " << root << endl; return; } do { string filename = data.cFileName; if (filename == "." || filename == "..") continue; string fullPath = root + "\\" + filename; if (data.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) { scanPath(fullPath); } else { set<string> exts = {"bat", "vbs", "js", "ps1", "cmd", "exe"}; string ext = filename.substr(filename.find_last_of('.') + 1); transform(ext.begin(), ext.end(), ext.begin(), ::tolower); if (exts.count(ext)) { fileCount++; if (isWhitelisted(fullPath)) { cout << "✅ 白名单跳过: " << fullPath << endl; continue; } if (isFileSuspicious(fullPath)) { suspiciousCount++; handleSuspiciousFile(fullPath); } } } } while (FindNextFileA(hFind, &data)); FindClose(hFind); } void scanCurrentDir() { char buffer[MAX_PATH]; GetCurrentDirectoryA(MAX_PATH, buffer); string current(buffer); cout << "🔍 正在扫描当前目录: " << current << "\n"; fileCount = 0; suspiciousCount = 0; scanPath(current); cout << "\n📊 扫描完成!共检查 " << fileCount << " 个脚本,发现 " << suspiciousCount << " 个可疑项。\n"; } void scanCustomDir() { string path; cout << "请输入要扫描的路径:\n>"; getline(cin, path); if (path.empty()) return; cout << "🔍 正在扫描: " << path << "\n"; fileCount = 0; suspiciousCount = 0; scanPath(path); cout << "\n📊 扫描完成!共检查 " << fileCount << " 个脚本,发现 " << suspiciousCount << " 个可疑项。\n"; } void scanAllDrives() { DWORD drives = GetLogicalDrives(); cout << "🔍 正在扫描所有磁盘...\n"; for (int i = 0; i < 26; ++i) { if (drives & (1 << i)) { string drive = string() + static_cast<char>('A' + i) + ":\\"; UINT type = GetDriveTypeA(drive.c_str()); if (type == DRIVE_FIXED || type == DRIVE_REMOVABLE) { cout << "\n🔍 开始扫描驱动器 " << drive << "\n"; fileCount = 0; suspiciousCount = 0; scanPath(drive); cout << "📊 " << drive << " 扫描完成:检查 " << fileCount << " 文件,发现 " << suspiciousCount << " 可疑项。\n"; } } } } void startRealTimeMonitor() { cout << "此功能暂未实现(文件级实时监控)。\n"; } void stopRealTimeMonitor() { g_monitoring = false; } void addFalsePositive() { cout << "请输入误报的进程名(如 chrome.exe):\n>"; string proc; getline(cin, proc); if (proc.empty()) return; g_trustedProcesses.insert(toLower(proc)); saveWhitelist(); cout << "✅ 已将 \"" << proc << "\" 添加为可信进程。\n"; log("Added false positive: " + proc); } void showMainMenu() { system("cls"); cout << "\n========== 🛡️ 杀毒工具 v9.0 ==========\n"; cout << "1. 扫描当前目录\n"; cout << "2. 扫描指定目录\n"; cout << "3. 扫描全盘\n"; cout << "4. 主动防御(实时监控)\n"; cout << "5. 管理隔离区\n"; cout << "6. 启用行为监控(动态防护)\n"; cout << "7. 添加误报程序(防误报)\n"; cout << "0. 退出\n>"; } int APIENTRY WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow) { SetConsoleOutputCP(936); SetConsoleCP(936); AllocConsole(); freopen("CONOUT$", "w", stdout); freopen("CONIN$", "r", stdin); if (!LoadPsapiFunction()) { MessageBoxA(nullptr, "⚠️ 无法加载 Psapi.dll", "警告", MB_OK | MB_ICONWARNING); } cout << "🛡️ 欢迎使用轻量化静态隔离杀毒软件\n"; loadWhitelist(); CreateDirectoryA(QUARANTINE_DIR.c_str(), nullptr); while (true) { showMainMenu(); char choice; cin >> choice; cin.ignore(); switch (choice) { case '1': scanCurrentDir(); break; case '2': scanCustomDir(); break; case '3': scanAllDrives(); break; case '4': cout << "此功能预留。\n"; break; case '5': manageQuarantine(); break; case '6': if (!g_monitoring) { g_monitoring = true; CreateThread(nullptr, 0, BehaviorMonitorThread, nullptr, 0, nullptr); cout << "✅ 行为监控已启用\n"; } else { cout << "⚠️ 行为监控已在运行\n"; } break; case '7': addFalsePositive(); break; case '0': if (g_monitoring) g_monitoring = false; if (hPsapi) FreeLibrary(hPsapi); FreeConsole(); MessageBoxA(nullptr, "👋 杀毒软件已退出", "提示", MB_OK); return 0; default: MessageBoxA(nullptr, "❌ 无效选择", "错误", MB_OK | MB_ICONERROR); } system("pause"); } } 还是不行
最新发布
11-10
#define _CRT_SECURE_NO_WARNINGS #include <cstring> #include <iostream> #include <fstream> #include <vector> #include <cctype> #include <algorithm> #include <cstdint> #include <limits> #include <stdexcept> size_t large_value = 1000; // 数学验证:确保值 ≤ 65,535 ($2^{16}-1$) if (large_value > std::numeric_limits<uint16_t>::max()) { // 超出范围处理策略 throw std::overflow_error("Value exceeds uint16_t maximum"); // 或:return error_code; // 返回错误码 } // 安全转换 uint16_t safe_value = static_cast<uint16_t>(large_value); // 安全转换 uint16_t safe_value = static_cast<uint16_t>(large_value); // 自定义内存分配器 class CourseAllocator { public: static void* allocate(size_t size) { return ::operator new(size); } static void deallocate(void* ptr, size_t size) { ::operator delete(ptr); } }; // 自定义向量类(替代std::vector) template <typename T> class LowLevelVector { private: T* data; size_t capacity; size_t size; public: LowLevelVector() : data(nullptr), capacity(0), size(0) {} ~LowLevelVector() { if (data) { for (size_t i = 0; i < size; ++i) { data[i].~T(); } CourseAllocator::deallocate(data, capacity * sizeof(T)); } } void push_back(const T& item) { if (size >= capacity) { size_t new_capacity = capacity ? capacity * 2 : 4; T* new_data = static_cast<T*>(CourseAllocator::allocate(new_capacity * sizeof(T))); for (size_t i = 0; i < size; ++i) { new (new_data + i) T(std::move(data[i])); data[i].~T(); } CourseAllocator::deallocate(data, capacity * sizeof(T)); data = new_data; capacity = new_capacity; } new (data + size) T(item); ++size; } T& operator[](size_t index) { return data[index]; } const T& operator[](size_t index) const { return data[index]; } size_t get_size() const { return size; } T* begin() { return data; } T* end() { return data + size; } const T* begin() const { return data; } const T* end() const { return data + size; } void remove(size_t index) { if (index >= size) return; data[index].~T(); for (size_t i = index; i < size - 1; ++i) { new (data + i) T(std::move(data[i + 1])); data[i + 1].~T(); } --size; } void clear() { for (size_t i = 0; i < size; ++i) { data[i].~T(); } size = 0; } }; // 课程类 class Course { private: uint16_t id; // 2字节ID char name[32]; // 固定长度名称 uint8_t credit; // 1字节学分 uint8_t max_capacity; // 1字节最大容量 uint8_t current_enrollment; // 1字节当前选课人数 uint8_t day; // 上课日(0-6代表周日至周六) uint8_t start_hour; // 开始小时(0-23) uint8_t end_hour; // 结束小时(0-23) public: Course() : id(0), credit(0), max_capacity(0), current_enrollment(0), day(0), start_hour(0), end_hour(0) { memset(name, 0, sizeof(name)); } Course(uint16_t id, const char* name, uint8_t credit, uint8_t max_capacity, uint8_t day, uint8_t start, uint8_t end) : id(id), credit(credit), max_capacity(max_capacity), current_enrollment(0), day(day), start_hour(start), end_hour(end) { strncpy(this->name, name, sizeof(this->name) - 1); this->name[sizeof(this->name) - 1] = '\0'; } // 自定义序列化方法 void serialize(std::fstream& fs) const { fs.write(reinterpret_cast<const char*>(this), sizeof(Course)); } // 反序列化 void deserialize(std::fstream& fs) { fs.read(reinterpret_cast<char*>(this), sizeof(Course)); } uint16_t get_id() const { return id; } const char* get_name() const { return name; } uint8_t get_credit() const { return credit; } uint8_t get_max_capacity() const { return max_capacity; } uint8_t get_current_enrollment() const { return current_enrollment; } uint8_t get_day() const { return day; } uint8_t get_start_hour() const { return start_hour; } uint8_t get_end_hour() const { return end_hour; } bool is_full() const { return current_enrollment >= max_capacity; } void enroll_student() { if (!is_full()) current_enrollment++; } void unenroll_student() { if (current_enrollment > 0) current_enrollment--; } }; // 学生类 class Student { private: uint32_t id; // 4字节学号 char name[20]; // 固定长度姓名 LowLevelVector<uint16_t> course_ids; // 选课ID集合 public: Student() : id(0) { memset(name, 0, sizeof(name)); } Student(uint32_t id, const char* name) : id(id) { strncpy(this->name, name, sizeof(this->name) - 1); this->name[sizeof(this->name) - 1] = '\0'; } // 自定义序列化 void serialize(std::fstream& fs) const { fs.write(reinterpret_cast<const char*>(&id), sizeof(id)); fs.write(reinterpret_cast<const char*>(name), sizeof(name)); uint16_t count = course_ids.get_size(); fs.write(reinterpret_cast<const char*>(&count), sizeof(count)); for (size_t i = 0; i < course_ids.get_size(); ++i) { fs.write(reinterpret_cast<const char*>(&course_ids[i]), sizeof(uint16_t)); } } // 反序列化 void deserialize(std::fstream& fs) { fs.read(reinterpret_cast<char*>(&id), sizeof(id)); fs.read(reinterpret_cast<char*>(name), sizeof(name)); uint16_t count; fs.read(reinterpret_cast<char*>(&count), sizeof(count)); for (uint16_t i = 0; i < count; ++i) { uint16_t course_id; fs.read(reinterpret_cast<char*>(&course_id), sizeof(course_id)); course_ids.push_back(course_id); } } uint32_t get_id() const { return id; } const char* get_name() const { return name; } const LowLevelVector<uint16_t>& get_course_ids() const { return course_ids; } bool add_course(uint16_t course_id) { for (size_t i = 0; i < course_ids.get_size(); i++) { if (course_ids[i] == course_id) { return false; // 已经选过该课程 } } course_ids.push_back(course_id); return true; } bool remove_course(uint16_t course_id) { for (size_t i = 0; i < course_ids.get_size(); i++) { if (course_ids[i] == course_id) { course_ids.remove(i); return true; } } return false; } }; // 时间冲突检测系统(使用位图) class ScheduleConflictDetector { private: // 使用二维位图:7天,每天24小时,每小时用一个uint64_t表示(最多可以表示64门课程) uint64_t schedule_map[7][24] = { {0} }; public: // 检查课程在时间上是否已有课程冲突 bool check_conflict(const Course& course) const { uint8_t day = course.get_day(); uint8_t start = course.get_start_hour(); uint8_t end = course.get_end_hour(); for (uint8_t hour = start; hour < end; hour++) { if (schedule_map[day][hour] != 0) { return true; // 该时间段已有课程 } } return false; } // 注册课程时间 void register_course(const Course& course) { uint8_t day = course.get_day(); uint8_t start = course.get_start_hour(); uint8_t end = course.get_end_hour(); uint16_t id = course.get_id(); for (uint8_t hour = start; hour < end; hour++) { schedule_map[day][hour] |= (1ULL << (id % 64)); // 使用课程ID的低6位 } } // 清除课程时间 void unregister_course(const Course& course) { uint8_t day = course.get_day(); uint8_t start = course.get_start_hour(); uint8_t end = course.get_end_hour(); uint16_t id = course.get_id(); for (uint8_t hour = start; hour < end; hour++) { schedule_map[day][hour] &= ~(1ULL << (id % 64)); } } }; // 选课系统核心 class CourseSelectionSystem { private: LowLevelVector<Course> courses; LowLevelVector<Student> students; ScheduleConflictDetector conflict_detector; public: // 添加课程 bool add_course(const Course& course) { if (conflict_detector.check_conflict(course)) { return false; // 时间冲突 } conflict_detector.register_course(course); courses.push_back(course); return true; } // 学生选课 bool enroll_course(uint32_t student_id, uint16_t course_id) { Student* student = find_student(student_id); Course* course = find_course(course_id); if (!student || !course) { return false; } if (course->is_full()) { return false; } if (!student->add_course(course_id)) { return false; // 已经选过 } course->enroll_student(); return true; } // 学生退课 bool unenroll_course(uint32_t student_id, uint16_t course_id) { Student* student = find_student(student_id); Course* course = find_course(course_id); if (!student || !course) { return false; } if (!student->remove_course(course_id)) { return false; // 未选该课程 } course->unenroll_student(); return true; } // 查找学生 Student* find_student(uint32_t student_id) { for (size_t i = 0; i < students.get_size(); i++) { if (students[i].get_id() == student_id) { return &students[i]; } } return nullptr; } // 查找课程 Course* find_course(uint16_t course_id) { for (size_t i = 0; i < courses.get_size(); i++) { if (courses[i].get_id() == course_id) { return &courses[i]; } } return nullptr; } // 添加学生 void add_student(const Student& student) { students.push_back(student); } // 获取课程列表 const LowLevelVector<Course>& get_courses() const { return courses; } // 获取学生列表 const LowLevelVector<Student>& get_students() const { return students; } // 序列化整个系统 void serialize(const char* filename) { std::fstream fs(filename, std::ios::binary | std::ios::out); if (!fs) { std::cerr << "无法打开文件进行写入: " << filename << std::endl; return; } // 写入魔数标识版本 uint32_t magic = 0x43535359; // 'CSSY' uint16_t version = 0x0100; // 版本1.0 fs.write(reinterpret_cast<const char*>(&magic), sizeof(magic)); fs.write(reinterpret_cast<const char*>(&version), sizeof(version)); // 写入课程数量学生数量 uint32_t course_count = courses.get_size(); uint32_t student_count = students.get_size(); fs.write(reinterpret_cast<const char*>(&course_count), sizeof(course_count)); fs.write(reinterpret_cast<const char*>(&student_count), sizeof(student_count)); // 写入课程 for (size_t i = 0; i < course_count; ++i) { courses[i].serialize(fs); } // 写入学生 for (size_t i = 0; i < student_count; ++i) { students[i].serialize(fs); } fs.close(); } // 反序列化 void deserialize(const char* filename) { std::fstream fs(filename, std::ios::binary | std::ios::in); if (!fs) { std::cerr << "无法打开文件进行读取: " << filename << std::endl; return; } uint32_t magic; uint16_t version; fs.read(reinterpret_cast<char*>(&magic), sizeof(magic)); fs.read(reinterpret_cast<char*>(&version), sizeof(version)); if (magic != 0x43535359 || version != 0x0100) { std::cerr << "文件格式不匹配或版本不支持" << std::endl; return; } uint32_t course_count; uint32_t student_count; fs.read(reinterpret_cast<char*>(&course_count), sizeof(course_count)); fs.read(reinterpret_cast<char*>(&student_count), sizeof(student_count)); // 读取课程 for (uint32_t i = 0; i < course_count; ++i) { Course course; course.deserialize(fs); courses.push_back(course); conflict_detector.register_course(course); } // 读取学生 for (uint32_t i = 0; i < student_count; ++i) { Student student; student.deserialize(fs); students.push_back(student); } fs.close(); } }; // 控制台界面 class ConsoleUI { private: CourseSelectionSystem system; public: void show_main_menu() { while (true) { std::cout << "\n===== 学生选课系统 =====\n"; std::cout << "1. 管理员模式\n"; std::cout << "2. 学生模式\n"; std::cout << "3. 保存系统状态\n"; std::cout << "4. 加载系统状态\n"; std::cout << "0. 退出\n"; std::cout << "=======================\n"; std::cout << "请选择: "; int choice; std::cin >> choice; switch (choice) { case 1: show_admin_menu(); break; case 2: show_student_menu(); break; case 3: system.serialize("system.dat"); std::cout << "系统状态已保存.\n"; break; case 4: system.deserialize("system.dat"); std::cout << "系统状态已加载.\n"; break; case 0: return; default: std::cout << "无效选择!\n"; } } } private: void show_admin_menu() { while (true) { std::cout << "\n===== 管理员菜单 =====\n"; std::cout << "1. 添加课程\n"; std::cout << "2. 添加学生\n"; std::cout << "3. 查看课程列表\n"; std::cout << "4. 查看学生列表\n"; std::cout << "0. 返回主菜单\n"; std::cout << "=======================\n"; std::cout << "请选择: "; int choice; std::cin >> choice; switch (choice) { case 1: add_course(); break; case 2: add_student(); break; case 3: display_courses(); break; case 4: display_students(); break; case 0: return; default: std::cout << "无效选择!\n"; } } } void show_student_menu() { uint32_t student_id; std::cout << "请输入学生ID: "; std::cin >> student_id; if (!system.find_student(student_id)) { std::cout << "学生ID不存在!\n"; return; } while (true) { std::cout << "\n===== 学生菜单 (" << student_id << ") =====\n"; std::cout << "1. 查看可选课程\n"; std::cout << "2. 选课\n"; std::cout << "3. 退课\n"; std::cout << "4. 查看已选课程\n"; std::cout << "0. 返回主菜单\n"; std::cout << "============================\n"; std::cout << "请选择: "; int choice; std::cin >> choice; switch (choice) { case 1: display_available_courses(student_id); break; case 2: enroll_course(student_id); break; case 3: unenroll_course(student_id); break; case 4: display_enrolled_courses(student_id); break; case 0: return; default: std::cout << "无效选择!\n"; } } } void add_course() { uint16_t id; char name[32]; uint8_t credit, capacity, day, start, end; std::cout << "输入课程ID: "; std::cin >> id; std::cout << "输入课程名称: "; std::cin.ignore(); std::cin.getline(name, sizeof(name)); std::cout << "输入学分: "; std::cin >> credit; std::cout << "输入最大容量: "; std::cin >> capacity; std::cout << "输入上课日(0-6 周日-周六): "; std::cin >> day; std::cout << "输入开始小时(0-23): "; std::cin >> start; std::cout << "输入结束小时(0-23): "; std::cin >> end; Course course(id, name, credit, capacity, day, start, end); if (system.add_course(course)) { std::cout << "课程添加成功!\n"; } else { std::cout << "课程添加失败(时间冲突)!\n"; } } void add_student() { uint32_t id; char name[20]; std::cout << "输入学生ID: "; std::cin >> id; std::cout << "输入学生姓名: "; std::cin.ignore(); std::cin.getline(name, sizeof(name)); Student student(id, name); system.add_student(student); std::cout << "学生添加成功!\n"; } void display_courses() { const auto& courses = system.get_courses(); std::cout << "\n课程列表:\n"; std::cout << "ID\t名称\t学分\t容量\t已选\t时间\n"; for (size_t i = 0; i < courses.get_size(); i++) { const Course& c = courses[i]; std::cout << c.get_id() << "\t" << c.get_name() << "\t" << static_cast<int>(c.get_credit()) << "\t" << static_cast<int>(c.get_max_capacity()) << "\t" << static_cast<int>(c.get_current_enrollment()) << "\t" << "周" << static_cast<int>(c.get_day()) << " " << static_cast<int>(c.get_start_hour()) << ":00-" << static_cast<int>(c.get_end_hour()) << ":00\n"; } } void display_students() { const auto& students = system.get_students(); std::cout << "\n学生列表:\n"; std::cout << "ID\t姓名\n"; for (size_t i = 0; i < students.get_size(); i++) { const Student& s = students[i]; std::cout << s.get_id() << "\t" << s.get_name() << "\n"; } } void display_available_courses(uint32_t student_id) { const auto& courses = system.get_courses(); const Student* student = system.find_student(student_id); std::cout << "\n可选课程列表:\n"; std::cout << "ID\t名称\t学分\t容量\t已选\t时间\n"; for (size_t i = 0; i < courses.get_size(); i++) { const Course& c = courses[i]; // 检查是否已选 bool enrolled = false; const auto& enrolled_courses = student->get_course_ids(); for (size_t j = 0; j < enrolled_courses.get_size(); j++) { if (enrolled_courses[j] == c.get_id()) { enrolled = true; break; } } if (!enrolled && !c.is_full()) { std::cout << c.get_id() << "\t" << c.get_name() << "\t" << static_cast<int>(c.get_credit()) << "\t" << static_cast<int>(c.get_max_capacity()) << "\t" << static_cast<int>(c.get_current_enrollment()) << "\t" << "周" << static_cast<int>(c.get_day()) << " " << static_cast<int>(c.get_start_hour()) << ":00-" << static_cast<int>(c.get_end_hour()) << ":00\n"; } } } void display_enrolled_courses(uint32_t student_id) { const Student* student = system.find_student(student_id); if (!student) { std::cout << "学生不存在!\n"; return; } std::cout << "\n已选课程列表:\n"; std::cout << "ID\t名称\t学分\t时间\n"; const auto& course_ids = student->get_course_ids(); for (size_t i = 0; i < course_ids.get_size(); i++) { Course* course = system.find_course(course_ids[i]); if (course) { std::cout << course->get_id() << "\t" << course->get_name() << "\t" << static_cast<int>(course->get_credit()) << "\t" << "周" << static_cast<int>(course->get_day()) << " " << static_cast<int>(course->get_start_hour()) << ":00-" << static_cast<int>(course->get_end_hour()) << ":00\n"; } } } void enroll_course(uint32_t student_id) { uint16_t course_id; std::cout << "输入要选的课程ID: "; std::cin >> course_id; if (system.enroll_course(student_id, course_id)) { std::cout << "选课成功!\n"; } else { std::cout << "选课失败(课程已满、不存在或已选)!\n"; } } void unenroll_course(uint32_t student_id) { uint16_t course_id; std::cout << "输入要退的课程ID: "; std::cin >> course_id; if (system.unenroll_course(student_id, course_id)) { std::cout << "退课成功!\n"; } else { std::cout << "退课失败(未选该课程或课程不存在)!\n"; } } }; int main() { ConsoleUI ui; ui.show_main_menu(); return 0; }
06-22
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值