免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
最近访问板块 发新帖
查看: 1884 | 回复: 8
打印 上一主题 下一主题

[C++] 一道看似很简单的题目,函数如何记录上一次的记录 [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2008-12-13 23:18 |只看该作者 |倒序浏览
初一看这道题,感觉非常简单,很容易搞定,如果从实现类似的功能的角度来看,还是可以非常快的速度写出来。只是,题中给出了不少东西,意味着不能随意写东西了。

      我现在遇到的问题是:slice(NULL, seps);

      如何记录原来的slice(str, seps)中传入的str;

      如果在类的基础上的话,弄一个静态参数可以搞定,但是这里却是一个函数,目前说来,我非常困惑,我现在唯一能想到的是记录到硬盘里。

    sos

已知一个函数定义如下:
const char* slice(char* str, const char* seps);
这个函数能把字符串str,以seps为边界,切割成许多小块儿。具体用法如下所示:
void test()
{
  char* str = "A quick_red#fox jumps over the lazy brown dog##".
  const char* seps = " _#";
  const char* piece;
  piece = slice(str, seps); // get the first slice. str is
modified in the process.
  while(piece)
  {
  cout << piece << " ";
  piece = slice(NULL, seps); // NULL means to continue
slicing the previous string.
  };
}
这个函数的输出为:A quick red fox jumps over the lazy brown dog
说明:
a、slice这个函数会更改被切割字符串,自动加入一些\0结尾。
b、多个连续的分隔符当成一个分隔符。比如"A###B"得到"A"和"B",没有空字符串。
c、第一个参数为NULL时,会继续切割上一次没有切割完毕的字符串。
d、如果切割完成,没有新的片断了,返回NULL
请写代码实现slice函数。

论坛徽章:
0
2 [报告]
发表于 2008-12-13 23:46 |只看该作者
在slice.h头文件中定义一个全局变量
在slice.c里用extern 引用这个变量来存贮用户给的字符串。
注意这个变量内存的申请的释放(当需要返回NULL的时候我觉得就可以释放内存了,当输入的第一个参数不为NULL的时候也应该释放并申请内存来存储这个参数的指)

论坛徽章:
0
3 [报告]
发表于 2008-12-13 23:52 |只看该作者
用static,请参考strtok的实现。
#if defined(LIBC_SCCS) && !defined(lint)
static char sccsid[] = "@(#)strtok.c&nbsp;&nbsp;&nbsp;&nbsp;8.1 (Berkeley) 6/4/93";
#endif /* LIBC_SCCS and not lint */
#include <sys/cdefs.h>
__FBSDID("$FreeBSD: src/lib/libc/string/strtok.c,v 1.9 2002/09/07 02:53:19 tjr Exp $");

#include <stddef.h>
#ifdef DEBUG_STRTOK
#include <stdio.h>
#endif
#include <string.h>

char&nbsp;&nbsp;&nbsp;&nbsp;*__strtok_r(char *, const char *, char **);

__weak_reference(__strtok_r, strtok_r);

char *
__strtok_r(char *s, const char *delim, char **last)
{
&nbsp;&nbsp;&nbsp;&nbsp;char *spanp, *tok;
&nbsp;&nbsp;&nbsp;&nbsp;int c, sc;

&nbsp;&nbsp;&nbsp;&nbsp;if (s == NULL && (s = *last) == NULL)
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;return (NULL);

&nbsp;&nbsp;&nbsp;&nbsp;/*
&nbsp;&nbsp;&nbsp;&nbsp; * Skip (span) leading delimiters (s += strspn(s, delim), sort of).
&nbsp;&nbsp;&nbsp;&nbsp; */

cont:
&nbsp;&nbsp;&nbsp;&nbsp;c = *s++;
&nbsp;&nbsp;&nbsp;&nbsp;for (spanp = (char *)delim; (sc = *spanp++) != 0;) {
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if (c == sc)
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;goto cont;
&nbsp;&nbsp;&nbsp;&nbsp;}

&nbsp;&nbsp;&nbsp;&nbsp;if (c == 0) {&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;/* no non-delimiter characters */
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*last = NULL;
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;return (NULL);
&nbsp;&nbsp;&nbsp;&nbsp;}
&nbsp;&nbsp;&nbsp;&nbsp;tok = s - 1;

&nbsp;&nbsp;&nbsp;&nbsp;/*
&nbsp;&nbsp;&nbsp;&nbsp; * Scan token (scan for delimiters: s += strcspn(s, delim), sort of).
&nbsp;&nbsp;&nbsp;&nbsp; * Note that delim must have one NUL; we stop if we see that, too.
&nbsp;&nbsp;&nbsp;&nbsp; */

&nbsp;&nbsp;&nbsp;&nbsp;for (;;) {
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;c = *s++;
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;spanp = (char *)delim;
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;do {
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if ((sc = *spanp++) == c) {
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if (c == 0)
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;s = NULL;
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;else
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;s[-1] = '\0';
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;*last = s;
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;return (tok);
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;} while (sc != 0);
&nbsp;&nbsp;&nbsp;&nbsp;}
&nbsp;&nbsp;&nbsp;&nbsp;/* NOTREACHED */
}

char *
strtok(char *s, const char *delim)
{
&nbsp;&nbsp;&nbsp;&nbsp;static char *last;

&nbsp;&nbsp;&nbsp;&nbsp;return (__strtok_r(s, delim, &last));
}

论坛徽章:
0
4 [报告]
发表于 2008-12-13 23:53 |只看该作者

回复 #2 FuriousFive 的帖子

汗~可不可以不使用全部变量,如果使用全局变量的话,自己就搞定了。
现在想知道:

    slice(NULL, seps);

      如何记录原来的slice(str, seps)中传入的str;

是否有const方面的东西可以解决这种问题,没有相关的经验,不知道可否~

论坛徽章:
0
5 [报告]
发表于 2008-12-13 23:55 |只看该作者
忘了还有静态变量的事了
谢谢三楼

论坛徽章:
0
6 [报告]
发表于 2008-12-14 00:14 |只看该作者
汗死,原来函数里也可以使用static,搞定问题了,我的问题解决了

非常感谢
FuriousFive
Fixend

论坛徽章:
0
7 [报告]
发表于 2008-12-14 00:17 |只看该作者
一起感谢Fixend
哈哈

论坛徽章:
3
天蝎座
日期:2014-10-25 13:44:312015年辞旧岁徽章
日期:2015-03-03 16:54:152015年迎新春徽章
日期:2015-03-04 09:48:31
8 [报告]
发表于 2008-12-14 09:02 |只看该作者
原帖由 FuriousFive 于 2008-12-13 23:46 发表
在slice.h头文件中定义一个全局变量
在slice.c里用extern 引用这个变量来存贮用户给的字符串。
注意这个变量内存的申请的释放(当需要返回NULL的时候我觉得就可以释放内存了,当输入的第一个参数不为NULL的时 ...



最好不要把全局变量定义在.h中;

最好定义在.c中,
在.h中extern;

论坛徽章:
0
9 [报告]
发表于 2008-12-14 11:04 |只看该作者
嗯,对的
头文件应该是声明的地方
而不是定义的地方
疏忽了
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP