字符串提取

发布于 2024-07-09 22:43:56 字数 1066 浏览 9 评论 0原文

目前我正在使用 C++ 环境开发非常基本的游戏。 这款游戏曾经是一个学校项目,但现在我已经完成了编程课程,我想扩展我的技能,并在这项旧作业上更加出色。

我已经做出了很多令我满意的改变。 我已将所有数据集中到文件夹层次结构中,并且已获得读取这些位置的代码。

然而,我的问题源于一个一直困扰着我的非常根本的缺陷。

为了访问我正在使用的图像数据,我使用了代码:

string imageLocation = "..\\DATA\\Images\\";

string bowImage = imageLocation + "bow.png";

问题是,当玩家在游戏板上拿起一个项目时,我的代码应该使用代码:

hud.addLine("You picked up a " + (*itt)->name() + "!");

打印到命令行,“你选择了举起弓来!”。 但它显示“您拿起了..\DATA\Images\!”。

在集中数据之前,我曾经使用:

name_(item_name.substr(0, item_name.find('.')))

在我的 Item 类构造函数中将项目名称截取为弓或蜡烛之类的名称。 在更改数据的结构方式后,我意识到我必须更改将名称简化为相同简单的“弓”或“蜡烛”的方式。

我已经更改了上面的代码以反映我对数据结构的更改:

name_(item_name.substr(item_name.find("..\\DATA\\Images\\"), item_name.find(".png")))

但不幸的是,正如我之前提到的,代码的更改并没有像我计划的那样工作。

现在我已经对我的问题进行了冗长的介绍,这是我的问题。

如何提取不需要的两个部分之间的字符串中间部分? 此外,您的目标中间部分的长度未知。

非常感谢你们提供的任何帮助。 如果您需要更多信息,请询问; 我将非常乐意上传部分甚至整个代码以获得更多帮助。 再次非常感谢您。

Currently I am working very basic game using the C++ environment. The game used to be a school project but now that I am done with that programming class, I wanted to expand my skills and put some more flourish on this old assignment.

I have already made a lot of changes that I am pleased with. I have centralized all the data into folder hierarchies and I have gotten the code to read those locations.

However my problem stems from a very fundamental flaw that has been stumping me.

In order to access the image data that I am using I have used the code:

string imageLocation = "..\\DATA\\Images\\";

string bowImage = imageLocation + "bow.png";

The problem is that when the player picks up an item on the gameboard my code is supposed to use the code:

hud.addLine("You picked up a " + (*itt)->name() + "!");

to print to the command line, "You picked up a Bow!". But instead it shows "You picked up a ..\DATA\Images\!".

Before I centralized my data I used to use:

name_(item_name.substr(0, item_name.find('.')))

in my Item class constructor to chop the item name to just something like bow or candle. After I changed how my data was structured I realized that I would have to change how I chop the name down to the same simple 'bow' or 'candle'.

I have changed the above code to reflect my changes in data structure to be:

name_(item_name.substr(item_name.find("..\\DATA\\Images\\"), item_name.find(".png")))

but unfortunately as I alluded to earlier this change of code is not working as well as I planned it to be.

So now that I have given that real long winded introduction to what my problem is, here is my question.

How do you extract the middle of a string between two sections that you do not want? Also that middle part that is your target is of an unknown length.

Thank you so very much for any help you guys can give. If you need anymore information please ask; I will be more than happy to upload part or even my entire code for more help. Again thank you very much.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(6

み青杉依旧 2024-07-16 22:43:56

老实说,您可能是从错误的角度来处理这个问题的。

您的项目类应该在私有成员中包含一个字符串“bow”。 然后,函数 Item::GetFilePath 将(在运行时)执行“..\DATA\Images\” + this->name + “.png”。

“弓”项目对象的基本属性不是文件名bow.png,而是它是“弓”这一事实。 文件名只是一个派生属性。

In all honeasty, you're probably approaching this from the wrong end.

Your item class should have a string "bow", in a private member. The function Item::GetFilePath would then (at runtime) do "..\DATA\Images\" + this->name + ".png".

The fundamental property of the "bow" item object isn't the filename bow.png, but the fact that it's a "bow". The filename is just a derived proerty.

韬韬不绝 2024-07-16 22:43:56

假设我正确理解你的意思,你的问题的简短版本是:如何分割包含文件路径的字符串,以便删除路径和扩展名,只留下“标题”?

您需要 find_last_of 方法。 这消除了路径:

std::size_type lastSlash = filePath.find_last_of('\\');
if (lastSlash == std::string::npos)
    fileName = filePath;
else
    fileName = filePath.substr(lastSlash + 1);

请注意,您可能希望将常量定义为 \\ ,以防您需要为其他平台更改它。 并非所有操作系统文件系统都使用 \\ 来分隔路径段。

另请注意,您还需要使用 find_last_of 作为扩展名点,因为文件名通常可以在整个路径中包含点。 只有最后一个指示扩展的开始:

std::size_type lastDot = fileName.find_last_of('.');
if (lastDot == std::string::npos)
{
    title = fileName;
}
else
{
    title = fileName.substr(0, lastDot);
    extension = fileName.substr(lastDot + 1);
}

请参阅 http://msdn.microsoft.com/en-us/library/3y5atza0(VS.80).aspx

Assuming I understand you correctly, the short version of your question is: how do I split a string containing a file path so I have removed the path and the extension, leaving just the "title"?

You need the find_last_of method. This gets rid of the path:

std::size_type lastSlash = filePath.find_last_of('\\');
if (lastSlash == std::string::npos)
    fileName = filePath;
else
    fileName = filePath.substr(lastSlash + 1);

Note that you might want to define a constant as \\ in case you need to change it for other platforms. Not all OS file systems use \\ to separate path segments.

Also note that you also need to use find_last_of for the extension dot as well, because filenames in general can contain dots, throughout their paths. Only the very last one indicates the start of the extension:

std::size_type lastDot = fileName.find_last_of('.');
if (lastDot == std::string::npos)
{
    title = fileName;
}
else
{
    title = fileName.substr(0, lastDot);
    extension = fileName.substr(lastDot + 1);
}

See http://msdn.microsoft.com/en-us/library/3y5atza0(VS.80).aspx

就像说晚安 2024-07-16 22:43:56

使用 boost 文件系统:

#include "boost/filesystem.hpp"

namespace fs = boost::filesystem;

void some_function(void)
{
    string imageLocation = "..\\DATA\\Images\\";
    string bowImage = imageLocation + "bow.png";
    fs::path image_path( bowImage  ); 
    hud.addLine("You picked up a " + image_path.filename() + "!");  //prints: You picked up a bow!

using boost filesystem:

#include "boost/filesystem.hpp"

namespace fs = boost::filesystem;

void some_function(void)
{
    string imageLocation = "..\\DATA\\Images\\";
    string bowImage = imageLocation + "bow.png";
    fs::path image_path( bowImage  ); 
    hud.addLine("You picked up a " + image_path.filename() + "!");  //prints: You picked up a bow!
无人接听 2024-07-16 22:43:56

因此,结合保罗和我的想法,尝试这样的事情(为了可读性而进行了分解):

string extn = item_name.substr(item_name.find_last_of(".png"));
string path = item_name.substr(0, item_name.find("..\\DATA\\Images\\"));
name_ = item_name.substr( path.size(), item_name.size() - extn.size() );

如果您知道项目名称总是以“..DATA”等开头,则可以稍微简化一下(您可以存储它在常量中,不需要在字符串中搜索它)

编辑:按照 EarWicker 的建议,将扩展查找部分更改为使用 find_last_of(这可以避免路径包含“.png”的情况)扩展名之前的某处)

So combining Paul's and my thoughts, try something like this (broken down for readability):

string extn = item_name.substr(item_name.find_last_of(".png"));
string path = item_name.substr(0, item_name.find("..\\DATA\\Images\\"));
name_ = item_name.substr( path.size(), item_name.size() - extn.size() );

You could simplify it a bit if you know that item name always starts with "..DATA" etc (you could store it in a constant and not need to search for it in the string)

Edit: Changed extension finding part to use find_last_of, as suggested by EarWicker, (this avoids the case where your path includes '.png' somewhere before the extension)

心如荒岛 2024-07-16 22:43:56

item_name.find("..\DATA\Images\") 将返回子字符串“..\DATA\Images\”开始的索引,但似乎您希望索引位于它结束,所以你应该将“..\DATA\Images\”的长度添加到find返回的索引中。

另外,正如 hamishmcn 指出的那样, substr 的第二个参数应该是要返回的字符数,我认为这将是“.png”开始的索引减去“..\DATA\Images\”结束的索引。

item_name.find("..\DATA\Images\") will return the index at which the substring "..\DATA\Images\" starts but it seems like you'd want the index where it ends, so you should add the length of "..\DATA\Images\" to the index returned by find.

Also, as hamishmcn pointed out, the second argument to substr should be the number of chars to return, which would be the index where ".png" starts minus the index where "..\DATA\Images\" ends, I think.

蓝眸 2024-07-16 22:43:56

看起来错误的一件事是 substr 的第二个参数应该是要复制的字符数,而不是位置。

One thing that looks wrong is that the second parameter to substr should be the number of chars to copy, not the position.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文