//////////////////////////////////////////////////////////////////////////////// // // * Examples // // justin@justin-desktop:~/workspace/regtst/Debug$ ./regtst -e '^a(.*)c' 'a // b // c' // cflags |= REG_EXTENDED; // *** Flags *** // cflags = 0x1; // eflags = 0x0; // *** Regex *** // ^a(.*)c // *** Text *** // a // b // c // *** Substrings *** // \0 (0, 5): "a // b // c" // \1 (1, 4): " // b // " // justin@justin-desktop:~/workspace/regtst/Debug$ ./regtst -en '^a(.*)c' 'ac' // cflags |= REG_EXTENDED; // cflags |= REG_NEWLINE; // *** Flags *** // cflags = 0x5; // eflags = 0x0; // *** Regex *** // ^a(.*)c // *** Text *** // ac // *** Substrings *** // \0 (0, 2): "ac" // \1 (1, 1): "" // justin@justin-desktop:~/workspace/regtst/Debug$ // //////////////////////////////////////////////////////////////////////////////// #include <ctype.h> #include <stdio.h> #include <string.h> #include <unistd.h> #include <getopt.h> #include <sys/types.h> #include <regex.h> int main(int argc, char** argv) { int aRes, aCFlags, aEFlags; const char* aRegex; const char* aText; regex_t aReg; regmatch_t aMatch[32]; char aBuf[1024]; int aI, aLen; aCFlags = aEFlags = 0; while (1) { aRes = getopt(argc, argv, "eisnbc"); // REG_EXTENDED (e), REG_ICASE (i), REG_NOSUB (s), REG_NEWLINE (n), REG_NOTBOL (b), REG_NOTEOL (c). if (aRes == -1) break; switch(aRes) { case 'e': aCFlags |= REG_EXTENDED; printf("cflags |= REG_EXTENDED;\n"); break; case 'i': aCFlags |= REG_ICASE; printf("cflags |= REG_ICASE;\n" ); break; case 's': aCFlags |= REG_NOSUB; printf("cflags |= REG_NOSUB;\n"); break; case 'n': aCFlags |= REG_NEWLINE; printf("cflags |= REG_NEWLINE;\n"); break; case 'b': aEFlags |= REG_NOTBOL; printf("eflags |= REG_NOTBOL;\n"); break; case 'c': aEFlags |= REG_NOTEOL; printf("eflags |= REG_NOTEOL;\n"); break; default: // '?'. printf("Unknown option \"-%c\".\n", optopt); return 1; } } printf("*** Flags ***\ncflags = 0x%X;\neflags = 0x%X;\n", aCFlags, aEFlags); if ((optind + 2) != argc) { // GETOPT(3): By default, getopt() permutes the contents of argv as it // scans, so that eventually all the non-options are at the end. printf("Expected exactly 2 arguments (regex, text) beside options.\n"); return 2; } aRegex = argv[optind]; aText = argv[optind + 1]; printf("*** Regex ***\n%s\n", aRegex); printf("*** Text ***\n%s\n", aText); aRes = regcomp(&aReg, aRegex, aCFlags); if (aRes != 0) { regerror(aRes, &aReg, aBuf, sizeof(aBuf)); printf("Fail to compile the regex: %s\n", aBuf); return 3; } for(int aI = 0; aI < int(sizeof(aMatch) / sizeof(regmatch_t)); aI++) { aMatch[aI].rm_so = 77; aMatch[aI].rm_eo = 77; } // `regfree()' can be put right after the `regexec()' (see the example in // <http://www.opengroup.org/onlinepubs/000095399/functions/regcomp.html>) // but we are calling `regerror()' which needs a valid `regex_t'. aRes = regexec(&aReg, aText, sizeof(aMatch) / sizeof(regmatch_t), aMatch, aEFlags); if (aRes != 0) { regerror(aRes, &aReg, aBuf, sizeof(aBuf)); regfree(&aReg); printf("Problem occurs when execute the regex: %s\n", aBuf); return 4; } regfree(&aReg); printf("*** Substrings ***\n"); for (aI = 0; aI < int(sizeof(aMatch) / sizeof(regmatch_t)); aI++) { if (aMatch[aI].rm_so == -1) break; aLen = aMatch[aI].rm_eo - aMatch[aI].rm_so; strncpy(aBuf, aText + aMatch[aI].rm_so, aLen); aBuf[aLen] = 0; printf("\\%d (%d, %d): \"%s\"\n", aI, aMatch[aI].rm_so, aMatch[aI].rm_eo, aBuf); } return 0; }