将字符串转换为char * var []

时间:2019-01-26 03:35:37

标签: c++

尝试在cpp中做某事,我已经很长时间没有使用它了,它需要将一个字符串解析为char * var []。我似乎无法弄清楚。我目前的尝试是使用字符串流并以这种方式输入它,但是 EXC_BAD_ACC 不好。我能够找到的关于该错误的信息是,我正在将信息发送到某个地方,而它对此却无能为力。我在做什么错,应该怎么做

#include<iostream>
#include<unistd.h>
#include <stdio.h>
#include <string.h>
#include <sstream>
#define MAXLINE 80
using namespace std;


int main(int argc, char *argv[]){
    char *args[MAXLINE/2+1];
    bool ShouldRun = true;
    string hello;
    while(ShouldRun)
    {
        cout << "osh>";
        fflush(stdout);
        cin >> hello;
        int i = 0;

        stringstream ssin(hello);
        while(ssin.good() && 41){
            ssin >> args[i]; //errors here.
            ++i;
        }
    }
    return 0;
}

1 个答案:

答案 0 :(得分:2)

  

“我用strcpy尝试了该方法,它说char*char**不兼容”

该错误表明。在代码中,您将args声明为:

char *args[MAXLINE/2+1];

没有声明字符数组,而是声明了指向{em> char,其中MAXLINE/2+1的指针的数组。

现在,无论您是想要简单的c字符串还是想要它们的数组,您的代码都有些含糊。给定#define MAXLINE 80,然后对41进行检查,您似乎只需要一个c字符串而不是一个c字符串数组。在这种情况下,您只需要将声明更改为:

char args[MAXLINE/2+1];

这将创建一个41字节的 {em> char数组,该数组最多可存储40个字符(加上 nul终止字符)。要将hello转换为c字符串,只需使用.c_str()成员函数。 (请参见 cppreference.com - c_str),您需要先验证它是否适合hello.length()

将其放在一起,您可以:

#include <iostream>
#include <string>
#include <cstring>

#define MAXLINE 80

using namespace std;

int main (void) {

    char args[MAXLINE/2+1];     /* array of char - not pointers */
    bool ShouldRun = true;
    string hello;

    while(ShouldRun)
    {
        cout << "osh> ";
        if (!(cin >> hello))
            break;

        if (hello.length() <= MAXLINE/2) {  /* validate length of hello */
            strcpy (args, hello.c_str());       /* copy to args */
            cout << "args: " << args << '\n';   /* output args */
        }
    }
    return 0;
}

使用/输出示例

$ ./bin/string2c_str
osh> first_arg
args: first_arg
osh> second_arg
args: second_arg
osh> 

如果您要将所有输入存储为一个指针数组中的单独c字符串,那么您将需要分配存储空间并将开始地址分配给每个args[i],然后再复制到每个args或声明{{ 1}}作为固定大小的2D数组。让我知道您是否正在尝试这种方法。

使用指向Char的指针数组

要按照您的注释中的说明使用execvp,那么args实际上确实需要一个指针数组 char,其中您的下一个指针必须将最后一个参数明确设置为NULL,以指示参数结束。

还必须确保填充不超过MAXLINE/2个指针,而保留最后一个显式设置的NULL。您可以通过初始化设置所有指针NULL,然后为每个字符串分配hello.length() + 1个存储字符,在将c字符串复制到args[i]之前,将新块的起始地址分配给#include <string> #include <cstring> #define MAXLINE 80 using namespace std; int main (void) { char *args[MAXLINE/2+1] = {nullptr}; /* array of pointers to char */ bool ShouldRun = true; int n = 0; string hello; while(ShouldRun) { cout << "osh> "; if (n == MAXLINE/2 || !(cin >> hello)) { /* protect bounds */ cout << '\n'; break; } args[n] = new char [hello.length() + 1]; /* allocate storage */ strcpy (args[n++], hello.c_str()); /* copy to args[n] */ } n = 0; while (args[n]) { /* output args until NULL encountered */ cout << "args[" << n << "]: " << args[n] << '\n'; delete[] args[n++]; /* don't forget to free what you allocate */ } return 0; } 地址。

将这个示例放在一起,您将拥有:

EOF

注意:,在Linux(或)上使用 Ctrl + c 生成手册$ ./bin/string2c_str_array osh> arg_1 osh> arg_2 osh> arg_3 osh> args[0]: arg_1 args[1]: arg_2 args[2]: arg_3 来存储参数,直到读取循环退出为止在Windows上为Ctrl + z ))

使用/输出示例

mPlayer.addListener(object : IPlayerEventListener {
          override fun onPlayerStateChanged(playWhenReady: Boolean, playbackState: Int) {
               super.onPlayerStateChanged(playWhenReady, playbackState)
               if (playbackState == Player.STATE_READY) {
                    // Apply some logic here whenever you want to get the duration
                    var durationMillis = mPlayer.getDuration()

                    // Apply some logic here to send out the data to your servers (whether after video paused, resumed, stopped, your choice)
                    // Example (Assuming you use MVVM + RxJava + Retrofit, this is a common way to do network call)
                    viewModel.uploadPlaybackDetails(userId = 21, videoId = 18, playbackTime = durationMillis)
               }
          }

          override fun onPlayerError(error: ExoPlaybackException?) {
               super.onPlayerError(error)
               // Handle error here
          }
     })