首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Quotes bug随机间距c++

Quotes bug随机间距c++
EN

Stack Overflow用户
提问于 2019-11-24 12:51:18
回答 1查看 53关注 0票数 0

我尝试打印出一个接受标记( :<,:>)的文件,然后打印出输出(在:<和:>的位置插入双引号)。程序应该解析文件,然后打印引号来代替:< >:。

例如,提示符如下

代码语言:javascript
复制
Quotes without using "the special quote" characters. :!
Quotes using :< the special quote :> characters. :!
:< quote one :> :< quote two :> on the same line. :!
A quote mixed with a :< period :. :> on the end. :!
A quote next to a :< newline :> :!

其预期输出为

代码语言:javascript
复制
Quotes without using "the special quote" characters.
Quotes using "the special quote" characters.
"quote one" "quote two" on the same line.
A quote mixed with a "period." on the end.
A quote next to a "newline"

“:!”只是表示这是一个新行的开始。我目前的问题是,当它读取文件时,它会在第一个引号和结束引号之前添加一个空格。

代码语言:javascript
复制
   > Quotes without using "thespecial quote" characters.\n 
Exp: Quotes without using "the special quote" characters.\n
   > Quotes using "the special quote "characters.\n
Exp: Quotes using "the special quote" characters.\n
   >  "quote one" "quote two "on the same line.\n
Exp: "quote one" "quote two" on the same line.\n
   > A quote mixed with a "period. "on the end.\n
Exp: A quote mixed with a "period." on the end.\n
   > A quote next to a "newline"

我试图在我的代码中寻找空格,但是我找不到一个可靠的案例来检测所有的引号,然后什么都不打印出来。

我编写的函数接受传入main的数组(通过引用调用)

我认为问题出在我用引号替换标记的时候。我似乎找不到区分开始引号和结束引号标记(:<和:>)的方法。

下面是进入文本并替换:< :>标记的代码

代码语言:javascript
复制
 /****                                                                                                                                                                                                       
 * punctuation(char *pWord)                                                                                                                                                                                 
 * Gets the story and prints out the edited                                                                                                                                                                 
 * c-array without the markers.                                                                                                                                                                             
 ****/
void punctuation(char * Marker)
{
   //*(Marker) = ' ';                                                                                                                                                                                       
   if (*(Marker + 1) == '!')
   {
      *(Marker) = '\n';  //makes a newline when it detects :!
      *(Marker + 1) = 0;
   }
   else if (*(Marker + 1) == '>')
   {
      *(Marker) = '"'; // adds the starting quote :>
      *(Marker + 1) = 0;
   }
   else if (*(Marker + 1) == '<')
   {
      *(Marker) = '"'; // adds the ending quote <:
      *(Marker + 1) = 0;
   }
   else if (*(Marker + 1) == ',')
   {
      *(Marker) = ','; // adds a comma :,
      *(Marker + 1) = 0;
   }
   else if (*(Marker + 1) == '.')
   {
      *(Marker) = '.'; // adds a period when marker is :.
      *(Marker + 1) = 0;
   }

   return;
}

这是一个能正确显示所有内容的display函数,但当出现上面的文件时,它会随机添加空格。我已经能够让所有东西都正常工作(结束符、句号和逗号)。我似乎无法缩小代码添加空格的范围,尤其是当文件只包含<:和;>时

代码语言:javascript
复制
void display(char text[][256], int index) // text[][256] is the story, 
{

/****                                                                          
 * display(char text[][256], int len)                                         
 * Prints out the story. Call by reference.
 ****/
void display(char text[][256], int index)
{
   cout << endl;  
   for (int i = 0; i < index; i++)
   {
      if (*text [i + 1] == ',')
      {
         cout << text[i];
      }

      else if (*text [i + 1] == '.' || *text[i] == '.')
      {
         cout << text[i];
         if (isalpha(*text [i + 1]))
         {
            cout << " "; // don't touch
         }
      }

      else if (*text[i + 1] == '"'  || *text[i] == '"')
      {
         if (isalpha(*text[i + 1]))
         {
            cout << ' ';
            if (*text[i] == ' ')
            {
               cout << ' ';
            }
         }
         cout << text[i]; // adds the space for the colon
      }

      else if (*text[i] == ' ' && isalpha(*text[i + 1]))
      {
         cout << text[i] << " ";            
      }

      else
      {
         if (*text[i] == '\n')
         {
            cout << text[i];
         }
         else if (*text[i + 1] == ' ')
         {
            cout << text[i] << ""; // not this one
         }
         else if (*text[i] == ' ')
         {
            cout << text[i]; // dont touch at all
         }
         else if (isalpha(*text[i + 1]))
         {
            cout << text[i] << " "; // look at here
         }
         else
         {
            if (*text[i + 1] == '\n')
            {
               cout << text[i] << "";
            }
         }
      }
   }
   cout << endl;
}

我已经尝试执行cerr来查看数组输出,但我无法可靠地检测到结束引号,也无法修改我的标点符号方法以查看是否可以正常工作。任何建议都将不胜感激。

EN

回答 1

Stack Overflow用户

发布于 2019-11-24 17:58:53

您的问题已标记为C++。我看到的唯一的C++就是std::cout的用法

我可以看到原始指针,没有任何边界检查的C风格的数组,参数的指针衰减,字符数组而不是std::string

请允许我不调试您的代码。

相反,我会提出一个C++解决方案。你的主要目标似乎是替换文本。为此,C++有一个专门的函数:std::regex_replace

在我的示例程序中,我将从std::istream读取数据,在本例中为std::istringstream。但它也可以是以前以std::ifstream或任何其他std::istream的形式打开的文件,甚至是std::cin

输出将写入std::ostream,在本例中为std::cout。当然,这也可以是任何其他流。

在我使用带有代理类读取完整行的std::istream_iterator将文件读入std::vector之后,将使用std::transformstd::regex::replace搜索和替换文本

请参阅:

代码语言:javascript
复制
#include <iostream>
#include <algorithm>
#include <vector>
#include <sstream>
#include <string>
#include <iterator>
#include <regex>


class CompleteLine {    // Proxy for the input Iterator
public:
    // Overload extractor. Read a complete line
    friend std::istream& operator>>(std::istream& is, CompleteLine& cl) { std::getline(is, cl.completeLine); return is; }
    // Cast the type 'CompleteLine' to std::string
    operator std::string() const { return completeLine; }
protected:
    // Temporary to hold the read string
    std::string completeLine{};
};


// The source file. Please note. You can also open a file and use sourceFile as the ifstream.
std::istringstream sourceFile{ R"(Quotes without using "the special quote" characters. :!
Quotes using :< the special quote :> characters. :!
:< quote one :> :< quote two :> on the same line. :!
A quote mixed with a :< period :. :> on the end. :!
A quote next to a :< newline :> :!
)" };


int main() {
    // Read all lines of the source file into the vector. 
    std::vector<std::string> text(std::istream_iterator<CompleteLine>(sourceFile), {});

    // Search for text and replace it
    std::transform(text.begin(), text.end(), std::ostream_iterator<std::string>(std::cout,"\n"), [](std::string & s) {
        return std::regex_replace(std::regex_replace(std::regex_replace(s, 
            std::regex(":< | :>"), "\""),   // Replace  :< or  :>  with " 
            std::regex(" :!"), ""),         // Replace :! with nothing
            std::regex(" :."), "."); });    // Replace  :. with .

    return 0;
}

当然,还有许多其他可能的解决方案。。。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/59014775

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档