C++函数调用及满堂红概率检查程序问题咨询
一、函数间传递整数/字符串的基础方法
传递整数
- 值传递:直接传变量的值,函数内部修改不影响原变量,适合不需要修改原数据的场景:
void printNum(int num) { cout << num << endl; } // 调用:printNum(10); - 引用传递:传变量的引用,函数内部修改会同步到原变量,适合需要修改原数据或避免拷贝的场景:
void addOne(int& num) { num += 1; } // 调用:int a = 5; addOne(a); // 此时a变成6 - 指针传递:传变量的地址,和引用效果类似,是C风格的写法:
void addOne(int* num) { *num += 1; } // 调用:int a =5; addOne(&a);
传递字符串
用C++的std::string更安全,推荐用引用传递避免拷贝:
void printString(const string& str) { // const表示不修改原字符串 cout << str << endl; } // 调用:string s = "hello"; printString(s);
如果用C风格字符数组(char*),要注意空终止符,传递指针即可:
void printCStr(const char* str) { cout << str << endl; } // 调用:char s[] = "hello"; printCStr(s);
二、你的满堂红概率检查程序问题分析与改进
核心问题总结
- 类的定义与实现脱节:头文件里定义了
cards类,但cpp里的函数都是全局函数,没有作为类成员实现,导致类的成员变量完全没用到。 - 未初始化变量:
shufflewell里的deck数组未初始化就交换,DisplayCard里的i未赋值就访问deck[i],属于未定义行为。 - 无限递归:
DisplayCard最后写了return DisplayCard();,会无限调用自己,最终栈溢出。 - 变量作用域错误:
dealHand里试图访问DisplayCard的局部变量ranknames、R、S,这些变量只在DisplayCard内部有效,外部根本访问不到。 - main函数未实际调用功能:只是声明了
DisplayCard(),没有创建类对象、调用类的成员函数,自然没有输出。 - 头文件保护宏错误:
#ifndef Class.h和#define Class.h是错误写法,宏名不能包含小数点,应该用全大写的标识符比如CLASS_H。
改进后的代码
Class.h
#ifndef CLASS_H #define CLASS_H #include <iostream> #include <string> using namespace std; class cards { private: int deck[52]; // 把牌组定义为私有,通过成员函数操作,封装更合理 public: cards(); // 构造函数,初始化牌组 void shufflewell(); void displayCard(int cardIndex); // 显示单张牌,接收牌的索引 void dealHand(); // 发5张牌 bool isFullHouse(); // 判断是否是满堂红 }; #endif // CLASS_H
class.cpp
#include <iostream> #include "Class.h" #include <ctime> #include <cstdlib> #include <string> using namespace std; // 构造函数:初始化牌组,每张牌用0-51表示,0-12是黑桃A-K,13-25方块,以此类推 cards::cards() { for (int i = 0; i < 52; i++) { deck[i] = i; } } void cards::shufflewell() { srand(time(0)); // 只需要初始化一次随机种子,放在这里合适 for (int i = 0; i < 52; i++) { int j = rand() % 52; swap(deck[i], deck[j]); // 用标准swap函数更简洁 } } void cards::displayCard(int cardIndex) { string suitnames[4] = {"spades", "diamonds", "clubs", "hearts"}; string ranknames[13] = {"A", "2", "3", "4", "5", "6", "7", "8", "9", "10", "J", "Q", "K"}; int suitnumber = deck[cardIndex] / 13; int rank = deck[cardIndex] % 13; cout << ranknames[rank] << " of " << suitnames[suitnumber] << endl; } void cards::dealHand() { cout << "Your hand:" << endl; for (int i = 0; i < 5; i++) { displayCard(i); } } // 判断满堂红:有三张同点数+两张同点数 bool cards::isFullHouse() { int rankCount[13] = {0}; // 统计前5张牌的点数出现次数 for (int i = 0; i < 5; i++) { int rank = deck[i] % 13; rankCount[rank]++; } bool hasThree = false; bool hasTwo = false; for (int count : rankCount) { if (count == 3) hasThree = true; else if (count == 2) hasTwo = true; } return hasThree && hasTwo; }
main.cpp
#include <iostream> #include "Class.h" using namespace std; int main() { cout << "Full house probability checker" << endl; cards myCards; // 创建类对象 myCards.shufflewell(); // 洗牌 myCards.dealHand(); // 发牌 // 判断是否是满堂红并输出结果 if (myCards.isFullHouse()) { cout << "\nYou got a Full House!" << endl; } else { cout << "\nNo Full House this time." << endl; } return 0; }
你需要补的知识盲区
- 类与对象的基本使用:类的成员函数必须通过对象调用,理解成员变量的作用域和封装性。
- 变量作用域:局部变量只在当前函数/代码块内有效,外部无法访问。
- 随机数的正确使用:
srand(time(0))只需要调用一次,不要放在循环或重复调用的函数里。 - 未定义行为的危害:未初始化的变量会导致程序行为不可预测,必须避免。
- 递归的正确写法:递归必须有终止条件,否则会无限调用导致栈溢出。
内容的提问来源于stack exchange,提问作者TheUncleIroh30
相关产品推荐
相关产品推荐

