實現佔位符替換接口,同printf

導航語音實現方案(文尾附有源碼)

函數接口如下

 

char *textTranslate(char *content, …)

 

content:可變參列表中的固定參,包含佔位符的字符串;

…:可變參數;

返回值:爲替換後的字符串

使用時將佔位符所代表的值解析後,按照content中佔位符順序依次傳遞給可變參數列表,函數即可返回content所代表的實際內容,用法同printf(char*, …);

結合配置文件,實現可配置語音組合模式

佔位符定義

  • 1 佔位符定義

定義

含義

備註

@i

整形數據

代表所有int型數據,最大爲int取值範圍,可表示距離/角度等

@s

字符型數據

字符串,char*

如“前方100米上坡”

content表示爲:

  • 2 “前方100米上坡”的通用述方式

前方

@i

@s

 

 

函數接口與配置文件

配合配置文件可實現語音組合的來靈活配置,配置文件配置示例如下:

 

[導航語音]

beginNavi = “開始導航,向北偏南@i度方向出發,全程共@i米”

distanceNotice = “當前已行使@i米,還剩@i米完成本次機動任務”

keyPoint1 = “前方@i米路口@s”

[關鍵點類型]

key1 = “左轉”

key2 = “右轉”

key3 = “左調頭”

.

.

 [桅杆告警]

mastWarning = “桅杆升起,請勿行車”

[偏航告警]

yawWarning = “您已偏離預定航線”

 

函數使用舉例如下:

如播報配置文件中設置的開始導航語音條目:

beginNavi = “開始導航,向北偏南@a度方向出發,全程共@i米”時,調用方式如下:

beginNavi = textTranslate(beginNavi, 30, 100);

該函數將@a替換爲30,@i替換爲100,替換後的結果爲:

beginNavi = “開始導航,向北偏南30度方向出發,全程共100米”

開發者只需要從配置文件中選擇自己需要的條目,並將對應的數值傳遞按照順序傳遞給textTranslate函數即可。

函數實現

Algorithm.h

#ifndef ALGORITHM_H
#define ALGORITHM_H

class Algorithm
{
public:
    Algorithm();
    char *textTranslate(char *format,...);//數字不能以0開頭
private:
    char *replaceHolder(char *&str, char *replace, int pos);
    char *intToChar(int val);
};

#endif // ALGORITHM_H

Algorithm.cpp

#include "Algorithm.h"
#include <stdio.h>
#include<iostream>
#include<string.h>
#include<stdarg.h>

Algorithm::Algorithm()
{

}

char *Algorithm::replaceHolder(char *&str, char* replace ,int pos)
{
    if(str == nullptr)
        return nullptr;
    int lenTotal = strlen(str);
    int lenReplace;
    if(!replace)
        lenReplace = 0;
    else
        lenReplace = strlen(replace);
    int lenTail = lenTotal - pos - 2;
    char *strTotal = new char[lenTotal + lenReplace - 2 + 1];
    char *strTail = new char[lenTail];
    memcpy(strTail, str + pos + 2, lenTail);

    memcpy(strTotal, str, lenTotal);
    memcpy(strTotal + pos, replace, lenReplace);
    memcpy(strTotal + pos + lenReplace, strTail, lenTail);
    memcpy(strTotal + pos + lenReplace + lenTail, "\0",1);
    delete[] strTail;
    return strTotal;
}

char *Algorithm::textTranslate(char *format,...)
{
    va_list ap;
    char *p;
    int ival;
    char *s;
    if(!format)
    {
        return nullptr;
    }
    va_start(ap,format);

    int i = 0, j = 0;
    loop:
    for(i = j, p = format + i; *p; ++i, ++p)
       {
           if(*p != '@')
           {
               continue;
           }
           switch(*++p)
           {
               case 'i'://整形數據
                   ival = va_arg(ap,int);
                   s = intToChar(ival);
                   format = replaceHolder(format, s, i);
                   j = i + 1;
                   goto loop;
                   break;
               case 's'://字符數據
                   s = va_arg(ap,char *);
                   format = replaceHolder(format,s,i);
                   j = i + 1;
                   goto loop;
                   break;
               default:
                   break;
           }
       }
       va_end(ap);
       return format;
}

char *Algorithm::intToChar(int val)
{
    char *str = nullptr;
    int count = 0;
    int localValue = val;
    while(val%10 > 0)
    {
        count++;
        val = val/10;
    }
    str = new char[count];
    _itoa(localValue, str, 10);
    return str;
}

調用測試

main .cpp

#include <QCoreApplication>
#include "algorithm.h"

#ifdef WINDOWS
#include<windows.h>
#endif

#ifdef UNIX
#include<sys\timeb.h>
#endif
#include<iostream>
using namespace std;

int main(int argc, char *argv[])
{
    QCoreApplication a(argc, argv);

#ifdef WINDOWS
    DWORD tStart, tEnd;
    tStart = GetTickCount();
#endif
    Algorithm alg;
    char *tempp="hello @s hello @s!\n@i\n@i";
    char *aaa = alg.textTranslate(tempp,"world","windows",100,30);
    cout<<"aaa="<< aaa<<endl;

#ifdef WINDOWS
    tEnd = GetTickCount();
    DWORD tPeriod = tEnd - tStart;
    cout << "tStart=" << tStart << endl;
    cout<< "tEnd=" << tEnd << endl;
    cout << "period=" <<tPeriod<<endl;
#endif

    return a.exec();
}

輸出結果:

aaa=hello world hello windows!

100

30

tStart=259596406

tEnd=259596406

period=0

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章