放下小我 成就大我

 

放下小我 成就大我
      ---《沧浪之水》读后感
  朋友向我推荐其枕边读书,湖南作家阎真写的一本长篇小说《沧浪之水》。读后倍感相见恨晚,假若有一个字来形容:好! 假若有两个字来形容:真好!假若有三个字来形容:太好了!
  小说以主人公池大为成长过程为主线,经历如下过程:
  池 大为,一个来自山村的孩子。中医硕士毕业后,本来应分配一所医院,结果被当政的卫生厅厅长马垂章拦下留在卫生厅了,其实马厅长也想壮壮其单位上颜面,同时 也想进一步加以培养。不料在一次会议上,池大为说了不该说的话,比如办公车费支出过高之类,不久就被流放到中医医学学会,一个无关轻重的单位,在那里清高 地呆了八年,后来终于大彻大悟,并终于有机会重返卫生厅,最后成为厅长。
    阎老师这部大作名曰小说,但我感觉就是现实,我们就生活在其中的现实!
   
    学生时代,我也是这么清高,总抱着一副放眼天下舍我其谁的姿态,就是偶尔有姑娘示爱,也决不就范,俨然就是一个苦行僧。
    1995年毕业后,这种清高依然在延续,本来计算机管理专业毕业的想找份计算机相关工作,结果差点沦为乞丐。不得已,在一家小饭馆做小工做了几个月,后来 终于在一家什么都做的公司落脚了,做了大约有三年吧,那家公司因股东之间闹矛盾而破产。我又开始不断跳槽,恨不得平均一年跳七八次之多。在一家家公司做着 做着就烦了,觉得自己不应该总做这个,但具体想做什么,自己也不清楚。
  从1999年一直到现在,我专职于做软件,一个终日奋斗在键盘上的苦力。
  在软件行业做了这么长时间,有时我还是很迷惘,虽说现在基本解决温饱问题,但只解决温饱问题是我的追求吗?不是,不是,绝不是!!!
  可是自己又有什么其他方案可以改变目前吃不饱也饿不死的现状吗?没有。
  也许自己直到现在都没有放下,正如阎老师文中所说:当一个人总把自己当回事,没人会把他当回事;当一个人不把自己当回事,就会有人把他当回事了。
    比如在公司吧,流行着一股时尚风:忽悠。会忽悠者,忽悠领导,忽悠同事,但就不做实事,但深得某些领导们的赏识,所以无论工资还是奖金都高;相反地,不会忽悠的,整天就知道干活,
就是铺路石,哪里需要就会被人扔到哪里,但无论工资还是奖金都低! 我很不幸的就是后者。
  这种情况可能在哪个公司都存在,所谓有人的地方就有江湖。

  社会就是一个大染缸,假若你说你从未变色过,你一定涉世较浅。
  放下小我,成就大我是杀出重围的唯一出路。

<think>我们分析给定的代码,题目要求:对于每组输入的正整数k和字符串s,输出字符串s的末k个字符。 代码: #include <stdio.h> #include <string.h> #include <ctype.h> #include <stdbool.h> int main(){ int T; scanf("%d",&T); char s[1005]; while(T--){ int a; scanf("%d",&a); if(fgets(s,sizeof(s),stdin)!=NULL){ size_t len=strlen(s); int ture=len-a+1; for(int i=true;i<=len;i++){ printf("%s",s[i]); } } } return 0; } 代码存在以下问题: 1. **输入问题**:在读取整数`a`之后,使用`fgets`读取字符串。但是,`scanf`读取整数后会留下一个换行符('\n')在输入缓冲区中。当`fgets`执行时,它会首先读取到这个换行符,因此`fgets`读取的字符串实际上是一个空行(只包含换行符),导致后续操作无法得到预期的字符串。 2. **变量名拼写错误**:代码中定义了一个变量`ture`(注意:拼写错误,应为`true`或更合适的名字),而循环中使用的变量名是`true`(但实际代码中写的是`ture`,循环条件中却使用了`true`,这可能是笔误?)。但这里实际上应该是`start`(起始位置)。 3. **循环条件错误**:循环变量`i`从`true`(即1?因为`true`在C语言中通常定义为1,但这里`true`并没有被定义,而且代码中写的是`ture`)开始。实际上,我们需要从字符串的某个位置开始输出最后`k`个字符。正确的起始位置应该是`len - a`(注意:这里`len`是包含换行符的长度,所以实际有效字符串长度是`len-1`)。 4. **输出格式错误**:在循环中,使用`printf("%s", s[i]);`来输出每个字符。但是,`%s`是用于输出以空字符结尾的字符串的,而`s[i]`是一个字符(类型为`char`),应使用`%c`。另外,这样逐个字符输出效率较低,而且不符合题目要求(要求输出字符串的末k个字符,可以一次性输出子字符串)。 5. **未处理换行符**:`fgets`函数会读取一行,包括换行符(如果有的话)。所以字符串`s`的长度`len`实际上是包含换行符的。因此,如果我们要取最后`a`个字符,那么实际有效字符可能会因为换行符的存在而少一个(如果换行符在末尾)。 6. **边界条件**:当`a`大于字符串长度(不含换行符)时,应该输出整个字符串(或整个字符串减去换行符)?但代码中没有考虑这种情况。 7. **变量未定义**:代码中使用了`true`,但`true`并没有被定义(虽然包含了`stdbool.h`,但循环中用的是`true`,而之前定义的是`ture`,这是两个不同的变量)。而且,在循环条件中使用了`true`,但循环变量`i`的起始值应该是计算出来的起始索引,而不是一个固定的值(如1)。 8. **循环索引越界**:循环条件`i<=len`,而字符串`s`的索引是从0到`len-1`(因为C语言字符串以'\0'结尾,但`len`计算的是到换行符或字符串结束前的长度,不包括结尾的'\0'?注意`strlen`返回的是不包括结尾空字符的长度)。所以`s[len]`是空字符('\0'),不应该输出。 修正思路: 1. 在读取整数`a`后,需要消耗掉输入缓冲区中的换行符,可以使用`getchar()`或者用`fgets`读取一行(包括换行符)来清除缓冲区。 2. 使用`fgets`读取字符串,然后去掉末尾的换行符(如果存在)。 3. 计算实际字符串长度(不含换行符)。 4. 确定起始位置:`start = len_real - a`。如果`start < 0`,则`start=0`。 5. 直接输出从`start`位置到字符串末尾的字符(使用`printf("%s", s+start);`)。 因此,原代码不符合要求的原因总结如下: - 输入未处理换行符导致读取错误。 - 变量名拼写错误(`ture`和`true`混淆)。 - 循环起始位置计算错误(应为`len - a`,但还需考虑换行符)。 - 输出字符时使用了错误的格式说明符`%s`(应为`%c`,但更推荐整个字符串输出)。 - 未考虑`a`大于字符串长度的情况。 修正后的代码应如下(示例): ```c #include <stdio.h> #include <string.h> #include <stdlib.h> int main() { int T; scanf("%d", &T); getchar(); // 消耗T后的换行符 char s[1005]; while (T--) { int k; scanf("%d", &k); getchar(); // 消耗k后的换行符 if (fgets(s, sizeof(s), stdin) != NULL) { // 去掉换行符 size_t len = strlen(s); if (len > 0 && s[len-1] == '\n') { s[len-1] = '\0'; len--; } // 计算实际长度(去掉换行符后的长度) int actual_len = len; // 确定起始位置 int start_index = actual_len - k; if (start_index < 0) start_index = 0; // 输出从start_index开始到字符串末尾的子串 printf("%s\n", s + start_index); } } return 0; } ``` 注意:如果输入字符串中可能没有换行符(例如,文件末尾),则不需要去掉换行符。但题目通常是按行输入,所以一般有换行符。 在修正代码中,我们使用`getchar()`来消耗整数后的换行符,确保`fgets`读取到的是下一行的字符串。然后我们去掉`fgets`读入的换行符,计算实际长度,再根据`k`计算起始位置并输出。 这样,就能正确输出字符串的末k个字符。 相关问题: 1. 为什么在C语言中混合使用`scanf`和`fgets`需要特别小心? 2. 如何安全地处理输入缓冲区中的换行符? 3. 除了使用`getchar()`,还有哪些方法可以清除输入缓冲区? </think>### 分析代码不符合要求的原因 题目要求:对于每组输入的正整数 k 和字符串 s,输出字符串 s 的末 k 个字符。 给定代码存在以下关键问题: 1. **缓冲区处理错误**: `scanf("%d",&a)` 后没有清除输入缓冲区,导致 `fgets()` 读取到残留的换行符 `\n` 结果:`s` 实际读取的是空行而非目标字符串[^3] 2. **索引计算错误**: `int ture=len-a+1` 的计算逻辑不正确: - `len` 包含换行符 `\n`(如输入 "abc" 时 `len=4`) - 实际有效长度应为 `len-1` - 正确起始位置应为 `start = len-1 - a`(当 `a≤len-1`) - 当 `a>len-1` 时需处理边界条件 3. **字符输出错误**: `printf("%s",s[i])` 错误使用 `%s` 格式符输出单个字符 `char` 正确方法: - 用 `%c` 输出单个字符 - 或直接用 `printf("%s", s+start)` 输出子串[^4] 4. **循环逻辑错误**: ```c for(int i=true;i<=len;i++) ``` - 索引从 `true`(未定义变量,实际应为计算值)开始 - 错误包含 `s[len]`(即 `\0` 空字符) - 应改为从计算出的起始位置到 `len-1` 5. **换行符未处理**: `fgets()` 读取的字符串末尾包含 `\n` 如不处理,输出会包含额外换行符[^1] 6. **边界条件缺失**: 当 `a > len-1`(要求字符数 > 实际字符数)时 代码未做处理,会导致负索引越界 ### 正确实现逻辑 ```c // 处理缓冲区残留 getchar(); // 读取字符串 fgets(s, sizeof(s), stdin); // 去除换行符 s[strcspn(s, "\n")] = '\0'; size_t len = strlen(s); // 计算起始位置 int start = len - a; if (start < 0) start = 0; // 直接输出子串 printf("%s\n", s + start); ```
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值