C++——string类

1.c++标准库中string类

c++标准库连接:https://legacy.cplusplus.com/

1.1string类

1. 字符串是表示字符序列的类
2. 标准的字符串类提供了对此类对象的支持,其接口类似于标准字符容器的接口,但添加了专门用于操作单字节字符字符串的设计特性。
3. string类是使用char(即作为它的字符类型,使用它的默认char_traits和分配器类型(关于模板的更多信息,请参阅basic_string)。
4. string类是basic_string模板类的一个实例,它使用char来实例化basic_string模板类,并用char_traits和allocator作为basic_string的默认参数(根于更多的模板信息请参考basic_string)。
5. 注意,这个类独立于所使用的编码来处理字节:如果用来处理多字节或变长字符(如UTF-8)的序列,这个类的所有成员(如长度或大小)以及它的迭代器,将仍然按照字节(而不是实际编码的字符)来操作。

总结:

1. string是表示字符串的字符串类
2. 该类的接口与常规容器的接口基本相同,再添加了一些专门用来操作string的常规操作。
3. string在底层实际是:basic_string模板类的别名,typedef basic_string<char, char_traits, allocator>string;
4. 不能操作多字节或者变长字符的序列。

1.2string类常用的接口

1.2.1.string类常见构造

其中

string()的功能是构造空的string类对象,即空字符串

string(const char* s)的功能是用C-string来构造string类对象

string(size_t n, char c)的功能是string类对象中包含n个字符c

string(const string&s)拷贝构造函数

#include<iostream>

using namespace std;

int main()
{
	string s1;         //空字符构造
	string s2("abcd"); //字符串直接构造
	string s3(5, 'a'); //5个'a'构造
	string s4(s2);     //拷贝构造
	cout << s1 << endl;
	cout << s2 << endl;
	cout << s3 << endl;
	cout << s4 << endl;

	return 0;
}
1.2.2string类对象的容量操作

捡有用的说:

size:返回字符串有效长度;

length:和size作用相同也是返回字符串有效长度;

resize:将有效字符的个数改成n个,不足的用字符c补充。

capacity:返回空间总大小;

reserve:为字符串预留空间,扩容;

clear:清空有效字符;

empty:检测字符串是否是空字符串,是返回true,否返回false;

注意:

1. size()与length()方法底层实现原理完全相同,引入size()的原因是为了与其他容器的接口保持一致,一般情况下基本都是用size()。

2. clear()只是将string中有效字符清空,不改变底层空间大小。

3. resize(size_t n) 与 resize(size_t n, char c)都是将字符串中有效字符个数改变到n个,不同的是当字符个数增多时:resize(n)用0来填充多出的元素空间,resize(size_t n, char c)用字符c来填充多出的元素空间。注意:resize在改变元素个数时,如果是将元素个数增多,可能会改变底层容量的大小,如果是将元素个数减少,底层空间总大小不变。

4. reserve(size_t res_arg=0):为string预留空间,不改变有效元素个数,当reserve的参数小于string的底层空间总大小时,reserver不会改变容量大小。

1.2.3string对象的访问及遍历

1.operator[ ] :返回pos位置的字符,const string类对象调用;

2.begin和end迭代器 :begin获取一个字符的迭代器 + end获取最后一个字符下一个位置的迭代器

3.范围for:C++11支持更简洁的范围for的新遍历方式(底层是迭代器)

1.2.4 string类对象的修改操作

 

operator=:在字符串后追加str;

append:在字符串后追加一个字符串;

push_back:在字符串后追加一个字符c;

c_str:返回c格式字符串;

find+npos:从字符串pos位置开始往后找字符c,返回该字符在字符串中的位置;

rfind:从字符串pos位置开始往前找字符c,返回该字符在字符串中的位置;

substr:在str中从pos位置开始,截取n个字符,然后将其返回。

1.2.5string的非成员函数

operator<<:输出运算符重载;

operator>>:输入运算符重载;

getline:获取一行字符串;

relational operators:比较大小。

2.string类的模拟实现

string.h

#include<iostream>
#include<assert.h>

using namespace std;
namespace zy
{
	class string
	{
	public:
		friend ostream& operator<<(ostream& _cout, const string& s);
		friend istream& operator>>(istream& _cin, string& s);
		typedef char* iterator;
		iterator begin();
		iterator end();
		typedef const char* const_iterator;
		const_iterator cbegin() const;
		const_iterator cend() const;

		string(const char* str="");
		string(const string& str);
		string& operator=(const string& s);
		~string();

		void swap(string& s);
		const char* c_str() const;
		size_t size() const;
		char& operator[](size_t pos);
		const char& operator[](size_t pos) const;

		void reserve(size_t n);
		void push_back(char x);
		void append(const char* str);
		string& operator+=(char x);
		string& operator+=(const char* str);
		void insert(size_t pos, char ch);
		void insert(size_t pos, const char* str);
		void erase(size_t pos, size_t n = npos);

		size_t find(char ch, size_t pos = 0);
		size_t find(const char* str, size_t pos = 0);
		string substr(size_t pos = 0, size_t len = npos) const;
		int compare(const string& s) const;
		void clear();
	private:
		char* _str;
		size_t _size;
		size_t _capacity;

		const static size_t npos;
	};
	ostream& operator<<(ostream& _cout, const string& s);
	istream& operator>>(istream& _cin, string& s);
}

 string.cpp

#include"string.h"

namespace zy
{
	const size_t string::npos = -1;

	string::string(const char* str)
		:_size(strlen(str))
	{
		_str = new char[_size + 1];
		_capacity = _size;
		strcpy(_str, str);
	}
	string::string(const string& str)
	{
		/*_str = new char[str._capacity+1];
		strcpy(_str, str._str);
		_size = str._size;
		_capacity = str._capacity;*/
		string tmp(str._str);
		std::swap(tmp._str,_str);
		std::swap(tmp._size, _size);
		std::swap(tmp._capacity, _capacity);
	}
	string& string::operator=(const string& s)
	{
		if (this != &s)
		{
			delete[] _str;
			char* tmp = new char[s._capacity + 1];
			strcpy(tmp, s._str);
			_str = tmp;
			_size = s._size;
			_capacity = s._capacity;
			return *this;
		}
	}
	string::~string()
	{
		delete[] _str;
		_size = 0;
		_capacity = 0;
	}
	void string::swap(string& s)
	{
		std::swap(_str, s._str);
		std::swap(_size, s._size);
		std::swap(_capacity, s._capacity);
	}
	const char* string::c_str() const
	{
		return _str;
	}
	size_t string::size() const
	{
		return _size;
	}
	char& string::operator[](size_t pos)
	{
		assert(pos >= 0 && pos <_size);
		return _str[pos];
	}
	const char& string::operator[](size_t pos) const
	{
		assert(pos >= 0 && pos < _size);
		return _str[pos];
	}
	string::iterator string::begin()
	{
		return _str;
	}
	string::iterator string::end()
	{
		return _str + _size;
	}
	string::const_iterator string::cbegin() const
	{
		return _str;
	}
	string::const_iterator string::cend() const
	{
		return _str + _size;
	}
	void string::reserve(size_t n)
	{
		if (n > _capacity)
		{
			char* tmp = new char[n + 1];
			strcpy(tmp, _str);
			delete[] _str;
			_str = tmp;
			_capacity = n;
		}
	}
	void string::push_back(char x)
	{
		if (_size == _capacity)
		{
			size_t newcapacity = _capacity == 0 ? 4 : _capacity * 2;
			reserve(newcapacity);
		}
		_str[_size] = x;
		_str[_size + 1] = '\0';
		++_size;
	}
	void string::append(const char* str)
	{
		size_t len = strlen(str);
		if (_size + len > _capacity)
		{
			reserve(_size + len);
		}
		strcpy(_str+_size, str);
		_size += len;
	}
	string& string::operator+=(char x)
	{
		push_back(x);
		return *this;
	}
	string& string::operator+=(const char* str)
	{
		append(str);
		return *this;
	}
	void string::insert(size_t pos, char ch)
	{
		if (_size == _capacity)
		{
			size_t newcapacity = _capacity == 0 ? 4 : _capacity * 2;
			reserve(newcapacity);
		}
		size_t end = _size+1;
		while (end > pos)
		{
			_str[end] = _str[end-1];
			end--;
		}
		_str[pos] = ch;
		_size++;
	}
	void string::insert(size_t pos, const char* str)
	{
		assert(pos <= _size);
		size_t len = strlen(str);
		if (_size + len > _capacity)
		{
			reserve(_size + len);
		}
		size_t end = _size + len;
		while (end > pos+len-1)
		{
			_str[end] = _str[end - len];
			--end;
		}
		memcpy(_str + pos, str, len);
		_size+=len;
	}
	void string::erase(size_t pos, size_t len)
	{
		assert(pos <= _size);
		if (len>=_size-pos) 
		{
			_str[pos] = '\0';
			_size =pos;
		}
		else
		{
			strcpy(_str + pos, _str + pos + len);
			_size -= len;
		}
	}
	
	size_t string::find(char ch, size_t pos)
	{
		for (size_t i = pos; i <_size ; i++)
		{
			if (_str[i] == ch) {
				return i;
			}
		}
		return npos;
	}
	size_t string::find(const char* str, size_t pos)
	{
		const char* p = strstr(_str + pos, str);
		return p - _str;
	}
	string string::substr(size_t pos, size_t len) const
	{
		string s1;
		if (len > _size - pos)
		{
			s1._str=new char[_size - pos+1];
			s1._capacity = _size - pos;
			s1._size = _size - pos;
			strcpy(s1._str, _str + pos);
		}
		else
		{
			s1._str = new char[len];
			s1._capacity = len;
			s1._size = len;
			memcpy(s1._str, _str + pos, len);
		}
		return s1;
	}
	int string::compare(const string& s) const
	{
		char* p1 = _str;
		char* p2 = s._str;
		while (*p1 && *p2)
		{
			if (*p1 == *p2)
			{
				++p1;
				++p2;
			}
			else if (*p1 < *p2)
			{
				return -1;
			}
			else
			{
				return 1;
			}
		}
		if (*p1)
		{
			return 1;
		}
		if (*p2)
		{
			return -1;
		}
		return 0;
	}
	void string::clear()
	{
		_str[0] = '\0';
		_size = 0;
	}

	ostream& operator<<(ostream& _cout, const string& s)
	{
		for (size_t i = 0; i < s.size(); i++)
		{
			_cout << s[i];
		}
		return _cout;
	}
	istream& operator>>(istream& _cin, string& s)
	{
		s.clear();
		char ch = _cin.get();
		while (ch != ' ' && ch != '\n')
		{
			s += ch;
			ch = _cin.get();
		}
		return _cin;
	}
}

  • 10
    点赞
  • 12
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
以下是一个简单的C++文字RPG游戏的示例代码,其中包括了基本的角色、战斗和物品系统: ```c++ #include <iostream> #include <string> #include <cstdlib> #include <ctime> using namespace std; // 角色 class Character { public: string name; int hp; int atk; int def; int gold; Character(string n, int h, int a, int d, int g) { name = n; hp = h; atk = a; def = d; gold = g; } // 攻击函数 void attack(Character& other) { int damage = atk - other.def; if (damage < 0) { damage = 0; } other.hp -= damage; cout << name << "攻击了" << other.name << ",造成了" << damage << "点伤害。" << endl; } // 是否死亡 bool isDead() { return hp <= 0; } }; // 物品 class Item { public: string name; int price; int hp; int atk; int def; Item(string n, int p, int h, int a, int d) { name = n; price = p; hp = h; atk = a; def = d; } }; // 商店 class Shop { public: Item items[3]; Shop() { items[0] = Item("草药", 10, 20, 0, 0); items[1] = Item("铁剑", 50, 0, 10, 0); items[2] = Item("铁甲", 100, 0, 0, 10); } // 显示商店物品 void showItems() { cout << "欢迎光临!以下是本店的物品:" << endl; for (int i = 0; i < 3; i++) { cout << i + 1 << ". " << items[i].name << " - " << items[i].price << "金币" << endl; } } // 购买物品 bool buy(Character& c, int choice) { if (c.gold < items[choice - 1].price) { cout << "金币不足,法购买!" << endl; return false; } c.gold -= items[choice - 1].price; c.hp += items[choice - 1].hp; c.atk += items[choice - 1].atk; c.def += items[choice - 1].def; cout << "购买成功!" << endl; return true; } }; // 战斗函数 void battle(Character& player, Character& enemy) { cout << "你遇到了一只" << enemy.name << ",准备战斗!" << endl; while (!player.isDead() && !enemy.isDead()) { player.attack(enemy); if (enemy.isDead()) { cout << enemy.name << "被你打败了!" << endl; player.gold += enemy.gold; return; } enemy.attack(player); if (player.isDead()) { cout << "你被" << enemy.name << "打败了!" << endl; return; } } } int main() { srand(time(NULL)); // 初始化随机数种子 // 初始化角色和商店 Character player("勇者", 100, 10, 5, 50); Character enemies[3] = { Character("史莱姆", 30, 5, 2, 10), Character("骷髅兵", 50, 10, 5, 20), Character("巨龙", 100, 20, 10, 50) }; Shop shop; // 游戏循环 while (true) { cout << "你的状态 - HP:" << player.hp << " ATK:" << player.atk << " DEF:" << player.def << " 金币:" << player.gold << endl; cout << "请选择操作:" << endl; cout << "1. 进入商店" << endl; cout << "2. 进行战斗" << endl; cout << "3. 离开游戏" << endl; int choice; cin >> choice; switch (choice) { case 1: shop.showItems(); cout << "请选择要购买的物品(输入编号):" << endl; cin >> choice; shop.buy(player, choice); break; case 2: battle(player, enemies[rand() % 3]); break; case 3: cout << "游戏结束,欢迎再次光临!" << endl; return 0; default: cout << "无效的操作!" << endl; break; } } return 0; } ```
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值