如何解析这个通配符?

xixia07m 2017-07-23 06:44:46
要用一个全局变量suffixStr=_T(doc?)来涵盖两种文件类型即doc和docx, 我想用自定义函数的形式来实现这一功能,但是试过了不行,请大家帮我改改程序:

#include<iostream>
#include<string>
using namespace std;
void match(string strm) //match使等同于
{
string str1("x");
string str2;
if(strm.length()>0)
strm+="?";
// cout<<strm<<endl;
str2=strm;
str2+=str1;
if(str2.length()>0)
strm+="?";
// cout<<strm<<endl;
}
...全文
156 3 打赏 收藏 转发到动态 举报
写回复
用AI写文章
3 条回复
切换为时间正序
请发表友善的回复…
发表回复
赵4老师 2017-07-24
  • 打赏
  • 举报
回复
仅供参考:
#include <stdio.h>
#include <stdlib.h>
#include <ctype.h>

//摘自《代码之美》
//match2(regexp,text)
// 字符     含义
// .        匹配任意的单个字符
// ^        匹配输入字符串的开头
// $        匹配输入字符串的结尾
// *        匹配前一个字符的零个或者多个出现
int matchhere(char *regexp, char *text);
int matchstar(int c, char *regexp, char *text) {// matchstar: search for c*regexp at beginning of text
   do {// a * matches zero or more instances
       if (matchhere(regexp, text)) return 1;
   } while (*text != '\0' && (*text++ == c || c == '.'));
   return 0;
}
int matchhere(char *regexp, char *text) {// matchhere: search for regexp at beginning of text
   if (regexp[0] == '\0') return 1;
   if (regexp[1] == '*') return matchstar(regexp[0], regexp+2, text);
   if (regexp[0] == '$' && regexp[1] == '\0') return *text == '\0';
   if (*text!='\0' && (regexp[0]=='.' || regexp[0]==*text)) return matchhere(regexp+1, text+1);
   return 0;
}
int match2(char *regexp, char *text) {// match: search for regexp anywhere in text
    if (regexp[0] == '^') return matchhere(regexp+1, text);
    do {// must look even if string is empty
        if (matchhere(regexp, text)) return 1;
    } while (*text++ != '\0');
    return 0;
}

//match1(regexp,text)
// 字符     含义
// ?        匹配任意的单个字符
// *        匹配零个或者多个字符
int match_imp(const char *d,int dcur,const char *s,int scur) {
    if(!d[dcur]) return (!s[scur])?1:0;
    if (d[dcur]=='?') return match_imp(d,dcur+1,s,scur+1);
    else if(d[dcur]=='*') {
        do {
            if (match_imp(d,dcur+1,s,scur)) return 1;
        } while (s[scur++]);
        return 0;
    } else return (tolower(d[dcur])==tolower(s[scur]) && match_imp(d,dcur+1,s,scur+1))?1:0;
}
int match1(char* s1, char* s2) {
    return match_imp(s1,0,s2,0);
}

int main() {
    printf("%d==match1(abc ,abc)\n",match1("abc" ,"abc"));
    printf("%d==match1(a?c ,abc)\n",match1("a?c" ,"abc"));
    printf("%d==match1(a*c ,abc)\n",match1("a*c" ,"abc"));
    printf("-------------------\n");
    printf("%d==match1(abc ,abd)\n",match1("abc" ,"abd"));
    printf("%d==match1(a?c ,abd)\n",match1("a?c" ,"abd"));
    printf("%d==match1(a*c ,abd)\n",match1("a*c" ,"abd"));
    printf("\n");
    printf("%d==match2(abc ,abc)\n",match2("abc" ,"abc"));
    printf("%d==match2(^a  ,abc)\n",match2("^a"  ,"abc"));
    printf("%d==match2(c$  ,abc)\n",match2("c$"  ,"abc"));
    printf("%d==match2(a.c ,abc)\n",match2("a.c" ,"abc"));
    printf("%d==match2(a.*c,abc)\n",match2("a.*c","abc"));
    printf("-------------------\n");
    printf("%d==match2(ABC ,abc)\n",match2("ABC" ,"abc"));
    printf("%d==match2(^B  ,abc)\n",match2("^B"  ,"abc"));
    printf("%d==match2(A$  ,abc)\n",match2("A$"  ,"abc"));
    printf("%d==match2(a..c,abc)\n",match2("a..c","abc"));
    printf("%d==match2(a.*d,abc)\n",match2("a.*d","abc"));
    return 0;
}
//1==match1(abc ,abc)
//1==match1(a?c ,abc)
//1==match1(a*c ,abc)
//-------------------
//0==match1(abc ,abd)
//0==match1(a?c ,abd)
//0==match1(a*c ,abd)
//
//1==match2(abc ,abc)
//1==match2(^a  ,abc)
//1==match2(c$  ,abc)
//1==match2(a.c ,abc)
//1==match2(a.*c,abc)
//-------------------
//0==match2(ABC ,abc)
//0==match2(^B  ,abc)
//0==match2(A$  ,abc)
//0==match2(a..c,abc)
//0==match2(a.*d,abc)
//
xixia07m 2017-07-23
  • 打赏
  • 举报
回复
在对话框界面上有5个复选框,分别是doc/docx, pdf , ppt/pptx, xls/xlsx, txt,选中了文件类型后才能开始点击“选择路径”按钮,出现浏览文件夹对话框,选择完路径后,Clistctrl控件就得到了选中的文件类型的遍历文件结果,通过文件名,创建时间,路径三列显示出来,现在我要想让第一个复选框选上之后,就可以遍历.doc和docx两种类型的文件,但是只能在一个复选框单击响应程序中完成,即在void CremarksecretDlg::OnBnClickedCheck1()中完成,我应该怎么涵盖这两种文件类型,请您指点一下。

#include "stdafx.h"
#include "remarksecret.h"
#include "remarksecretDlg.h"
//#include "afxdialogex.h"
#include "Resource.h"
//#include "windows.h"
//#include <tchar.h>
#include <algorithm>
//#include <string>
#include <vector>
//#include <string>
//#include <iterator>
//#include <functional>

 

#ifdef _DEBUG
#define new DEBUG_NEW
#endif
using std::string; 
string suffixStr,suffixStr1,suffixStr2,suffixStr3,suffixStr4,suffixStr5;


 struct FileInfo
    {
	std::string szFileName;
	std::string szFilePath;
	std::string szCreateTime;
	};

 
  

// 用于应用程序“关于”菜单项的 CAboutDlg 对话框

class CAboutDlg : public CDialogEx
{
public:
	CAboutDlg();

// 对话框数据
	enum { IDD = IDD_ABOUTBOX };

	protected:
	virtual void DoDataExchange(CDataExchange* pDX);    // DDX/DDV 支持

// 实现
protected:
	DECLARE_MESSAGE_MAP()
};

CAboutDlg::CAboutDlg() : CDialogEx(CAboutDlg::IDD)
{
}

void CAboutDlg::DoDataExchange(CDataExchange* pDX)
{
	CDialogEx::DoDataExchange(pDX);	
}

BEGIN_MESSAGE_MAP(CAboutDlg, CDialogEx)
END_MESSAGE_MAP()


// CremarksecretDlg 对话框


CremarksecretDlg::CremarksecretDlg(CWnd* pParent /*=NULL*/)
	: CDialogEx(CremarksecretDlg::IDD, pParent)
{
	m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME);
}

void CremarksecretDlg::DoDataExchange(CDataExchange* pDX)
{
	CDialogEx::DoDataExchange(pDX);
	DDX_Control(pDX, IDC_LIST1, mlist);
}

BEGIN_MESSAGE_MAP(CremarksecretDlg, CDialogEx)
	ON_WM_SYSCOMMAND()
	ON_WM_PAINT()
	ON_WM_QUERYDRAGICON()
	ON_NOTIFY(LVN_ITEMCHANGED, IDC_LIST1, &CremarksecretDlg::OnLvnItemchangedList1)
	ON_BN_CLICKED(IDC_BUTTON1, &CremarksecretDlg::OnBnClickedButton1)
	ON_BN_CLICKED(IDC_CHECK1, &CremarksecretDlg::OnBnClickedCheck1)
	ON_BN_CLICKED(IDC_CHECK2, &CremarksecretDlg::OnBnClickedCheck2)
	ON_BN_CLICKED(IDC_CHECK3, &CremarksecretDlg::OnBnClickedCheck3)
	ON_BN_CLICKED(IDC_CHECK4, &CremarksecretDlg::OnBnClickedCheck4)
	ON_BN_CLICKED(IDC_CHECK5, &CremarksecretDlg::OnBnClickedCheck5)
END_MESSAGE_MAP()

/ TODO: 在此添加控件通知处理程序代码
	void CremarksecretDlg::OnBnClickedCheck1()
{
	// TODO: 在此添加控件通知处理程序代码
	int nstatus=(((CButton*)GetDlgItem(IDC_CHECK1))->GetCheck());
	if(nstatus=1)
	{
       suffixStr1=_T("doc?");//||suffixStr==_T("docx");	
	}
	else
	{
       suffixStr1=_T(" ");
	}
}
void CremarksecretDlg::OnBnClickedCheck2()
{
	// TODO: 在此添加控件通知处理程序代码
	//extern std::wstring suffixStr;

	int nstatus=(((CButton*)GetDlgItem(IDC_CHECK2))->GetCheck());
	if(nstatus=1)
	{
       suffixStr2=_T("pdf");
	}
	else
	{
        suffixStr2=_T(" ");
	}
}
void CremarksecretDlg::OnBnClickedCheck3()
{
	// TODO: 在此添加控件通知处理程序代码
	//extern std::wstring suffixStr;
	//match("ppt");
	int nstatus=(((CButton*)GetDlgItem(IDC_CHECK3))->GetCheck());
	if(nstatus=1)
	{
       suffixStr3=_T("ppt?");//||suffixStr==_T("pptx");	   
	}
	else
	{
       suffixStr3=_T(" ");
	}
}

//递归遍历所有文件
   void find (LPCTSTR lpPath,std::vector<FileInfo>&FileList)
 {
		//std::vector<FileInfo>fileList;
	    std::string szFind(lpPath);
		WIN32_FIND_DATA FindFileData;
		szFind+=_T("\\*.*");
		HANDLE hFind=::FindFirstFile(szFind.c_str(),&FindFileData);
		if(INVALID_HANDLE_VALUE==hFind) return;
		do//while(1)
		{
			if(FindFileData.dwFileAttributes&FILE_ATTRIBUTE_DIRECTORY)
				{//dir 目录在列表中可以双击打开,不要递归!
					if(FindFileData.cFileName[0]!='.') 
						{
							std::string szPath(lpPath);
							szPath+=_T("\\");
							szPath+=FindFileData.cFileName;
							TRACE1("%s\n",szPath.c_str());
							find(szPath.c_str(),FileList);   //自注:这里小写的fileList不行。
						}
				}
				else 
		        {//file
					std::string strFileName=FindFileData.cFileName;//文件名
					/*std::wstring*/suffixStr=strFileName.substr(strFileName.find_last_of('.')+1);
					if(suffixStr==suffixStr1)  //根据后缀选出自己感兴趣的文件,比如txt文件,注意大小写,如果想不区分大小写,需要自己统一转化为大写或小写然后比较
					 {
						FILETIME ft=FindFileData.ftCreationTime;   //取得创建时间
						SYSTEMTIME st={0};
						TCHAR buf[64]={0};
						FileTimeToLocalFileTime(&(FindFileData.ftCreationTime),&ft);    //转换成本地时间
						FileTimeToSystemTime(&ft,&st);     //在这句之前加上上一句,就不用再小时那里+8了。
						sprintf_s(buf,_T("%4d年-%02d月-%02d日%02d:%02d:%02d"),st.wYear,st.wMonth,st.wDay,st.wHour/*北京时间*/,st.wMinute,st.wSecond);
						std::string strFilePath=lpPath;
						strFilePath+=_T("\\");
						strFilePath+=FindFileData.cFileName;   //文件全路径名
						FileInfo fi;    //自注:结构变量不能代入
						fi.szFileName=strFileName;
						fi.szFilePath=strFilePath;
						fi.szCreateTime=buf;
						TRACE1("%s\n",strFileName.c_str());    //自注:这句是后加上的
						FileList.push_back(fi);  //自注:push_back(fi)是什么意思?
						//fi=FileList;
					 }
					else if(suffixStr==suffixStr2)  //根据后缀选出自己感兴趣的文件,比如txt文件,注意大小写,如果想不区分大小写,需要自己统一转化为大写或小写然后比较
					 {
						FILETIME ft=FindFileData.ftCreationTime;   //取得创建时间
						SYSTEMTIME st={0};
						TCHAR buf[64]={0};
						FileTimeToLocalFileTime(&(FindFileData.ftCreationTime),&ft);    //转换成本地时间
						FileTimeToSystemTime(&ft,&st);     //在这句之前加上上一句,就不用再小时那里+8了。
						sprintf_s(buf,_T("%4d年-%02d月-%02d日%02d:%02d:%02d"),st.wYear,st.wMonth,st.wDay,st.wHour,st.wMinute,st.wSecond);
						std::string strFilePath=lpPath;
						strFilePath+=_T("\\");       
						strFilePath+=FindFileData.cFileName;   //文件全路径名
						FileInfo fi;
						fi.szFileName=strFileName;
						fi.szFilePath=strFilePath;
						fi.szCreateTime=buf;
						FileList.push_back(fi);
					 }   
					 else if(suffixStr==suffixStr3)  //根据后缀选出自己感兴趣的文件,比如txt文件,注意大小写,如果想不区分大小写,需要自己统一转化为大写或小写然后比较
					 {
						FILETIME ft=FindFileData.ftCreationTime;   //取得创建时间
						SYSTEMTIME st={0};
						TCHAR buf[64]={0};
						FileTimeToLocalFileTime(&(FindFileData.ftCreationTime),&ft);    //转换成本地时间
						FileTimeToSystemTime(&ft,&st);     //在这句之前加上上一句,就不用再小时那里+8了。
						sprintf_s(buf,_T("%4d年-%02d月-%02d日%02d:%02d:%02d"),st.wYear,st.wMonth,st.wDay,st.wHour,st.wMinute,st.wSecond);
						std::string strFilePath=lpPath;
						strFilePath+=FindFileData.cFileName;   //文件全路径名
						FileInfo fi;
						fi.szFileName=strFileName;
						fi.szFilePath=strFilePath;
						fi.szCreateTime=buf;
						FileList.push_back(fi);
					 }
								   }
	    }while(::FindNextFile(hFind,&FindFileData));
 }    
			//FindClose(hFind);

#define BIF_NEWDIALOGSTYLE 0x0040

// CremarksecretDlg 消息处理程序

BOOL CremarksecretDlg::OnInitDialog()     //自注:这个函数是自动生成的
{
	CDialogEx::OnInitDialog();

	// 将“关于...”菜单项添加到系统菜单中。

	// IDM_ABOUTBOX 必须在系统命令范围内。
	ASSERT((IDM_ABOUTBOX & 0xFFF0) == IDM_ABOUTBOX);
	ASSERT(IDM_ABOUTBOX < 0xF000);

	CMenu* pSysMenu = GetSystemMenu(FALSE);
	if (pSysMenu != NULL)
	{
		BOOL bNameValid;
		CString strAboutMenu;
		bNameValid = strAboutMenu.LoadString(IDS_ABOUTBOX);
		ASSERT(bNameValid);
		if (!strAboutMenu.IsEmpty())
		{
			pSysMenu->AppendMenu(MF_SEPARATOR);
			pSysMenu->AppendMenu(MF_STRING, IDM_ABOUTBOX, strAboutMenu);
		}
	}

	// 设置此对话框的图标。当应用程序主窗口不是对话框时,框架将自动
	//  执行此操作
	SetIcon(m_hIcon, TRUE);			// 设置大图标
	SetIcon(m_hIcon, FALSE);		// 设置小图标

	ShowWindow(SW_MINIMIZE);

	// TODO: 在此添加额外的初始化代码
    mlist.SetExtendedStyle(mlist.GetExtendedStyle()|LVS_EX_GRIDLINES|LVS_EX_FULLROWSELECT); 
	mlist.InsertColumn(0,_T("操作"),LVCFMT_LEFT,80);//100指定每列宽度
	mlist.InsertColumn(1,_T("文件名"),LVCFMT_LEFT,500);
	mlist.InsertColumn(2,_T("创建时间"),LVCFMT_LEFT,120);
	mlist.InsertColumn(3,_T("路径"),LVCFMT_LEFT,360);
	return TRUE;  // 除非将焦点设置到控件,否则返回 TRUE
}

void CremarksecretDlg::OnSysCommand(UINT nID, LPARAM lParam)    //这个函数是自动生成的
{
	if ((nID & 0xFFF0) == IDM_ABOUTBOX)
	{
		CAboutDlg dlgAbout;
		dlgAbout.DoModal();
	}
	else
	{
		CDialogEx::OnSysCommand(nID, lParam);
	}
}

// 如果向对话框添加最小化按钮,则需要下面的代码
//  来绘制该图标。对于使用文档/视图模型的 MFC 应用程序,
//  这将由框架自动完成。

void CremarksecretDlg::OnPaint()    //这个函数是自动生成的
{
	if (IsIconic())
	{
		CPaintDC dc(this); // 用于绘制的设备上下文

		SendMessage(WM_ICONERASEBKGND, reinterpret_cast<WPARAM>(dc.GetSafeHdc()), 0);

		// 使图标在工作区矩形中居中
		int cxIcon = GetSystemMetrics(SM_CXICON);
		int cyIcon = GetSystemMetrics(SM_CYICON);
		CRect rect;
		GetClientRect(&rect);
		int x = (rect.Width() - cxIcon + 1) / 2;
		int y = (rect.Height() - cyIcon + 1) / 2;

		// 绘制图标
		dc.DrawIcon(x, y, m_hIcon);
	}
	else
	{
		CDialogEx::OnPaint();
	}
}

//当用户拖动最小化窗口时系统调用此函数取得光标
//显示。
HCURSOR CremarksecretDlg::OnQueryDragIcon()   //这个函数是自动生成的
{
	return static_cast<HCURSOR>(m_hIcon);
}





void CremarksecretDlg::OnBnClickedButton1()
{
	// TODO: 在此添加控件通知处理程序代码    自注:以下是我添加的代码
	BROWSEINFO bi; //BROWSEINFO结构有很多成员参数可以自己设置
	ZeroMemory(&bi,sizeof(BROWSEINFO)); //将以&bi为起始地址,大小为sizeof(BROWSEINFO)的内存区域用0填充 
	bi.ulFlags=BIF_BROWSEINCLUDEFILES; //设置弹出的对话框属性。此处意思为包含文件。如果不设这个值,默认的是只有文件夹。ulFlags还可以定义很多别的属性 
	bi.ulFlags=BIF_NEWDIALOGSTYLE; //窗口可以调整大小,有新建文件夹按钮
	LPITEMIDLIST pidl = SHBrowseForFolder(&bi); //Displays a dialog box enabling the user to select a Shell folder.
	TCHAR * path = new TCHAR[MAX_PATH];    //自注:点击按钮获得的地址在path变量中
	if(pidl!= NULL) 
	{ 
       SHGetPathFromIDList(pidl,path); //Converts an item identifier list to a file system path 
	   //MessageBox(path);
	}
	
	//FileInfo fileList;
	using std::vector; 
	vector<FileInfo>FileList;    //自注:程序不承认FileList是个结构变量
	//std::vector<FileInfo>fileList;
	find(/*_T("D:\\xsmposc\\XSMPos"*/path,FileList);   //取得文件信息,可自行插入列表框
	    //FileInfo fileList;
	   UINT nCount=FileList.size();   //得到控件的行数
	    //Filelist=fi;
	    int i;
	    CString empty;   
	    CString name;
	    CString time;
	    CString mypath;
	for(i=0;i<nCount;i++)
	{
		empty.Format(_T(""),i+1);
		mlist.InsertItem(i,empty);
		name.Format(_T("%s"),FileList[i].szFileName.c_str());
		mlist.SetItemText(i,1,name);      //插入列
		time.Format(_T("%s"),FileList[i].szCreateTime.c_str());
	    mlist.SetItemText(i,2,time);
		mypath.Format(_T("%s"),FileList[i].szFilePath.c_str());
		mlist.SetItemText(i,3,mypath);
	}	   	
	
}
以上程序省略了部分代码,贴出来的是主干。
战在春秋 2017-07-23
  • 打赏
  • 举报
回复
通配符没有必要使用,因为只判定doc和docx两种格式为正确格式,象下面这样就行。
#include "string.h"

bool match(char* src) {
	if ((!strcmp("doc",src)) || (!strcmp("docx",src)))
	{
		return true;
	}
	else
	{
		return false;
	}

}
int main() 
{
	bool ret1 = match("xls"); //ret1等于false
	bool ret2 = match("docw"); //ret2等于false
	bool ret3 = match("doc"); //ret3等于true
	bool ret4 = match("docx"); //ret4等于true
	return 0;
}

64,637

社区成员

发帖
与我相关
我的任务
社区描述
C++ 语言相关问题讨论,技术干货分享,前沿动态等
c++ 技术论坛(原bbs)
社区管理员
  • C++ 语言社区
  • encoderlee
  • paschen
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
  1. 请不要发布与C++技术无关的贴子
  2. 请不要发布与技术无关的招聘、广告的帖子
  3. 请尽可能的描述清楚你的问题,如果涉及到代码请尽可能的格式化一下

试试用AI创作助手写篇文章吧