Question: 求高手简化代码

谢谢     cfjtaishan自信男孩     谢谢      wodexiaojidan   学习了

#include <stdio.h>  static const int passdays[][12] = { 	0, 31, 59, 90, 120, 	151, 181, 212, 243,  	273, 304, 334, 	0, 31, 60, 91, 121, 	152, 182, 213, 244, 	274, 305, 335 };  static const char *weekday[] = { 	"MON", "TUE", "WEN", "THU",  	"FRI", "SAT", "SUN" };  static const int dayofmon[][12] = { 	31, 28, 31, 30, 	31, 30, 31, 31, 	30, 31, 30, 31, 	31, 29, 31, 30, 	31, 30, 31, 31, 	30, 31, 30, 31, };  static int FirstDayofYear(int year) { 	return (((year - 1) + (year - 1) / 4 - (year - 1) / 100 + (year - 1) / 400) % 7 + 1); }  static int FirstDayofMonth(int year, int month, int isleap) { 	int wday, mday;  	wday = FirstDayofYear(year); 	mday = (wday + passdays[isleap][month - 1]) % 7;  	return mday; }  static int WdayofToday(int year, int month, int day, int isleap) { 	int mday, tday;  	mday = FirstDayofMonth(year, month, isleap); 	tday = (mday + day - 1) % 7;  	return tday; }  static void Show(const char *s, const char *f, int day) { 	printf("%s%s%s\n", s, weekday[(day - 1 + 7) % 7], f); }  static char *NextDate(char *date, int year, int month, int day, int isleap) { 	int nyear, nmonth, nday;  	if(day == dayofmon[isleap][month - 1]){ 		nmonth = (month + 1) % 12; 		if(nmonth == 0){ 			nmonth = 12; 		}  		nday = 1; 	}else if(day >= 1 && day < dayofmon[isleap][month - 1]){ 		nmonth = month; 		nday = day + 1; 	} 	 	nyear = year + (nmonth < month);  	sprintf(date, ", %4d/%02d/%02d", nyear, nmonth, nday);  	return date; }  static char *FrontDate(char *date, int year, int month, int day, int isleap) { 	int fyear, fmonth, fday;  	if(day == 1){ 		fmonth = (month - 1 + 12) % 12; 		if(fmonth == 0){ 			fmonth = 12; 		}  		fday = dayofmon[isleap][fmonth - 1]; 	}else if(day > 1 && day <= dayofmon[isleap][month - 1]){ 		fmonth = month; 		fday = day - 1; 	}  	fyear = year - (fmonth > month);  	sprintf(date, ", %4d/%02d/%02d", fyear, fmonth, fday);  	return date; }  int main(void) { 	int year, month, day, tday, isleap, bcontinue; 	char date[16] = "";  	do{ 		scanf("%d%d%d", &year, &month, &day);  		if(year >= 1900 && year < 2100){ 			isleap = (year % 4 == 0 && year % 100 != 0 || year % 400 == 0);  			if(month >= 1 && month < 13){ 				bcontinue = (day >= 1 && day <= dayofmon[isleap][month - 1]); 			}else{ 				bcontinue = 0; 			} 		}else{ 			bcontinue = 0; 		} 	}while(!bcontinue);  	tday = WdayofToday(year, month, day, isleap);  	FrontDate(date, year, month, day, isleap); 	Show("Yesterday is ", date, tday - 1);  	NextDate(date, year, month, day, isleap); 	Show("Tomorrow is ", date, tday + 1);  	return 0; }

#include <stdio.h>  static const int passdays[][12] = { 	0, 31, 59, 90, 120, 	151, 181, 212, 243,  	273, 304, 334, 	0, 31, 60, 91, 121, 	152, 182, 213, 244, 	274, 305, 335 };  static const char *weekday[] = { 	"MON", "TUE", "WEN", "THU",  	"FRI", "SAT", "SUN" };  static const int dayofmon[][12] = { 	31, 28, 31, 30, 	31, 30, 31, 31, 	30, 31, 30, 31, 	31, 29, 31, 30, 	31, 30, 31, 31, 	30, 31, 30, 31, };  static int FirstDayofYear(int year) { 	return (((year - 1) + (year - 1) / 4 - (year - 1) / 100 + (year - 1) / 400) % 7 + 1); }  static int FirstDayofMonth(int year, int month, int isleap) { 	int wday, mday;  	wday = FirstDayofYear(year); 	mday = (wday + passdays[isleap][month - 1]) % 7;  	return mday; }  static int WdayofToday(int year, int month, int day, int isleap) { 	int mday, tday;  	mday = FirstDayofMonth(year, month, isleap); 	tday = (mday + day - 1) % 7;  	return tday; }  static void Show(const char *s, const char *f, int day) { 	printf("%s%s%s\n", s, weekday[(day - 1 + 7) % 7], f); }  static char *NextDate(char *date, int year, int month, int day, int isleap) { 	int nyear, nmonth, nday;  	if(day == dayofmon[isleap][month - 1]){ 		nmonth = (month + 1) % 13; 		if(nmonth == 0){ 			nmonth = 1; 		}  		nday = 1; 	}else if(day >= 1 && day < dayofmon[isleap][month - 1]){ 		nmonth = month; 		nday = day + 1; 	} 	 	nyear = year + (nmonth < month);  	sprintf(date, ", %4d/%02d/%02d", nyear, nmonth, nday);  	return date; }  static char *FrontDate(char *date, int year, int month, int day, int isleap) { 	int fyear, fmonth, fday;  	if(day == 1){ 		fmonth = (month - 1 + 12) % 13; 		if(fmonth == 0){ 			fmonth = 1; 		}  		fday = dayofmon[isleap][fmonth - 1]; 	}else if(day > 1 && day <= dayofmon[isleap][month - 1]){ 		fmonth = month; 		fday = day - 1; 	}  	fyear = year - (fmonth > month);  	sprintf(date, ", %4d/%02d/%02d", fyear, fmonth, fday);  	return date; }  int main(void) { 	int year, month, day, tday, isleap, bcontinue; 	char date[16] = "";  	do{ 		scanf("%d%d%d", &year, &month, &day);  		if(year >= 1900 && year < 2100){ 			isleap = (year % 4 == 0 && year % 100 != 0 || year % 400 == 0);  			if(month >= 1 && month < 13){ 				bcontinue = (day >= 1 && day <= dayofmon[isleap][month - 1]); 			}else{ 				bcontinue = 0; 			} 		}else{ 			bcontinue = 0; 		} 	}while(!bcontinue);  	tday = WdayofToday(year, month, day, isleap);  	FrontDate(date, year, month, day, isleap); 	Show("Yesterday is ", date, tday - 1);  	NextDate(date, year, month, day, isleap); 	Show("Tomorrow is ", date, tday + 1);  	return 0; }  2017 1 1 Yesterday is SAT, 2016/12/31 Tomorrow is MON, 2017/01/02  2017 2 1 Yesterday is TUE, 2017/01/31 Tomorrow is THU, 2017/02/02  2016 12 25 Yesterday is SAT, 2016/12/24 Tomorrow is MON, 2016/12/26  2016 2 28 Yesterday is SAT, 2016/02/27 Tomorrow is MON, 2016/02/29  2016 2 29 Yesterday is SUN, 2016/02/28 Tomorrow is TUE, 2016/03/01  2017 2 28 Yesterday is MON, 2017/02/27 Tomorrow is WEN, 2017/03/01

#include <stdio.h>  struct date_t {     int year;     int month;     int day; }; int gmonth[] = {31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};  int is_leap(int year); void tomorrow(struct date_t *ptm); void yesterday(struct date_t *ptm);  int main(void) {     struct date_t tm;     int y, m, d;      do {         scanf("%d%d%d", &y, &m, &d);         if (is_leap(y) && m == 2 && d == 29)             break;     } while (m > 12 || m <= 0 || d > gmonth[m-1] || d <= 0);      tm.year = y;     tm.month = m;     tm.day = d - 1;     yesterday(&tm);     printf("%4d-%02d-%02d's yesterday is %4d-%02d-%02d\n", y, m, d, tm.year, tm.month, tm.day);      tm.year = y;     tm.month = m;     tm.day = d + 1;     tomorrow(&tm);     printf("%4d-%02d-%02d's tomorrow  is %4d-%02d-%02d\n", y, m, d, tm.year, tm.month, tm.day);      return 0; }   int is_leap(int year) {     if ((year % 4 == 0 && year % 100 != 0)         || year % 400 == 0)         return 1;      return 0; }  void yesterday(struct date_t *ptm) {     if (ptm->day <= 0) {         ptm->month -= 1;         if (ptm->month <= 0) {             ptm->year -= 1;             if (ptm->year <= 0) {                 ptm->year = 0;                 ptm->month = 0;                 ptm->day = 0;                 return;             }             ptm->month = 12;             ptm->day = gmonth[ptm->month-1] + ptm->day;             return;         }         ptm->day = gmonth[ptm->month-1] + ptm->day;         if (ptm->month == 2 && is_leap(ptm->year))             ptm->day += 1;         return;     } }  void tomorrow(struct date_t *ptm) {     if (ptm->month == 2 && is_leap(ptm->year)         && ptm->day == gmonth[ptm->month - 1] + 1)         return;     if (ptm->day > gmonth[ptm->month - 1]) {         ptm->month += 1;         if (ptm->month > 12) {             ptm->year += 1;             ptm->month = 1;             ptm->day = 1;             return;         }         ptm->day = 1;         return;     } }  参考一下吧 就是比较比较多。

static int passdays[] = { 	0, 31, 59, 90, 120, 	151, 181, 212, 243,  	273, 304, 334 };  static char *weekday[] = { 	"MON", "TUE", "WEN", "THU",  	"FRI", "SAT", "SUN" };  static int FirstDayofYear(int year) { 	int i; 	if(year % 4 == 0 && year % 100 != 0 || year % 400 == 0){ 		for(i = 2; i < 12; ++i){ 			passdays[i] += 1; 		} 	}  	return (((year - 1) + (year - 1) / 4 - (year - 1) / 100 + (year - 1) / 400) % 7 + 1); }  static int FirstDayofMonth(int year, int month) { 	int wday, mday;  	wday = FirstDayofYear(year); 	mday = (wday + passdays[month - 1]) % 7;  	return mday; }  static WdayofToday(int year, int month, int day) { 	int mday, tday; 	 	mday = FirstDayofMonth(year, month); 	tday = (mday + day - 1) % 7;  	return tday; }  static void Show(const char *s, int day) { 	printf("%s%s\n", s, weekday[(day - 1 + 7) % 7]); }  int main(void) { 	int year, month, day, tday, isleap, bcontinue;  	do{ 		scanf("%d%d%d", &year, &month, &day);  		if(year >= 1900 && year < 2100){ 			isleap = (year % 4 == 0 && year % 100 != 0 || year % 400 == 0); 		 			if(month >= 1 && month < 13){ 				switch(month){ 					case 1: 					case 3: 					case 5: 					case 7: 					case 8: 					case 10: 					case 12: 						bcontinue = (day >= 1 && day < 32); 						break;  					case 4: 					case 6: 					case 9: 					case 11: 						bcontinue = (day >= 1 && day < 31);  					case 2: 						bcontinue = (isleap ? (day >= 1 && day < 30) : (day >= 1 && day < 29)); 						break; 					default: 						break; 				} 			}else{ 				bcontinue = 0; 			} 		}else{ 			bcontinue = 0; 		} 	}while(!bcontinue);  	tday = WdayofToday(year, month, day);  	Show("Yesterday is ", tday - 1); 	Show("Tomorrow is ", tday + 1);  	return 0; }


Question: C语言 文件指针与fseek

fopen, _wfopen Open a file.  FILE *fopen( const char *filename, const char *mode );  FILE *_wfopen( const wchar_t *filename, const wchar_t *mode );  Function Required Header Compatibility  fopen <stdio.h> ANSI, Win 95, Win NT  _wfopen <stdio.h> or <wchar.h> Win NT    For additional compatibility information, see Compatibility in the Introduction.  Libraries  LIBC.LIB Single thread static library, retail version  LIBCMT.LIB Multithread static library, retail version  MSVCRT.LIB Import library for MSVCRT.DLL, retail version    The c, n, and t mode options are Microsoft extensions for fopen and _fdopen and should not be used where ANSI portability is desired.  Return Value  Each of these functions returns a pointer to the open file. A null pointer value indicates an error.   Parameters  filename  Filename  mode  Type of access permitted  Remarks  The fopen function opens the file specified by filename. _wfopen is a wide-character version of fopen; the arguments to _wfopen are wide-character strings. _wfopen and fopen behave identically otherwise.  Generic-Text Routine Mappings  TCHAR.H Routine  _UNICODE & _MBCS Not Defined _MBCS Defined _UNICODE Defined  _tfopen fopen fopen _wfopen    The character string mode specifies the type of access requested for the file, as follows:  "r"  Opens for reading. If the file does not exist or cannot be found, the fopen call fails.  "w"  Opens an empty file for writing. If the given file exists, its contents are destroyed.  "a"  Opens for writing at the end of the file (appending) without removing the EOF marker before writing new data to the file; creates the file first if it doesn’t exist.  "r+"  Opens for both reading and writing. (The file must exist.)  "w+"  Opens an empty file for both reading and writing. If the given file exists, its contents are destroyed.  "a+"  Opens for reading and appending; the appending operation includes the removal of the EOF marker before new data is written to the file and the EOF marker is restored after writing is complete; creates the file first if it doesn’t exist.  When a file is opened with the "a" or "a+" access type, all write operations occur at the end of the file. The file pointer can be repositioned using fseek or rewind, but is always moved back to the end of the file before any write operation is carried out. Thus, existing data cannot be overwritten.  The "a" mode does not remove the EOF marker before appending to the file. After appending has occurred, the MS-DOS TYPE command only shows data up to the original EOF marker and not any data appended to the file. The "a+" mode does remove the EOF marker before appending to the file. After appending, the MS-DOS TYPE command shows all data in the file. The "a+" mode is required for appending to a stream file that is terminated with the CTRL+Z EOF marker.  When the "r+", "w+", or "a+" access type is specified, both reading and writing are allowed (the file is said to be open for “update”). However, when you switch between reading and writing, there must be an intervening fflush, fsetpos, fseek, or rewind operation. The current position can be specified for the fsetpos or fseek operation, if desired.  In addition to the above values, the following characters can be included in mode to specify the translation mode for newline characters:  t  Open in text (translated) mode. In this mode, CTRL+Z is interpreted as an end-of-file character on input. In files opened for reading/writing with "a+", fopen checks for a CTRL+Z at the end of the file and removes it, if possible. This is done because using fseek and ftell to move within a file that ends with a CTRL+Z, may cause fseek to behave improperly near the end of the file.   Also, in text mode, carriage return–linefeed combinations are translated into single linefeeds on input, and linefeed characters are translated to carriage return–linefeed combinations on output. When a Unicode stream-I/O function operates in text mode (the default), the source or destination stream is assumed to be a sequence of multibyte characters. Therefore, the Unicode stream-input functions convert multibyte characters to wide characters (as if by a call to the mbtowc function). For the same reason, the Unicode stream-output functions convert wide characters to multibyte characters (as if by a call to the wctomb function).  b  Open in binary (untranslated) mode; translations involving carriage-return and linefeed characters are suppressed.   If t or b is not given in mode, the default translation mode is defined by the global variable _fmode. If t or b is prefixed to the argument, the function fails and returns NULL.   For more information about using text and binary modes in Unicode and multibyte stream-I/O, see Text and Binary Mode File I/O and Unicode Stream I/O in Text and Binary Modes.  c  Enable the commit flag for the associated filename so that the contents of the file buffer are written directly to disk if either fflush or _flushall is called.  n  Reset the commit flag for the associated filename to “no-commit.” This is the default. It also overrides the global commit flag if you link your program with COMMODE.OBJ. The global commit flag default is “no-commit” unless you explicitly link your program with COMMODE.OBJ.  Valid characters for the mode string used in fopen and _fdopen correspond to oflag arguments used in _open and _sopen, as follows.  Characters in mode String Equivalent oflag Value for _open/_sopen   a _O_WRONLY | _O_APPEND (usually _O_WRONLY | _O_CREAT | _O_APPEND)  a+ _O_RDWR | _O_APPEND (usually _O_RDWR | _O_APPEND | _O_CREAT )  r _O_RDONLY  r+ _O_RDWR  w _O_WRONLY (usually _O_WRONLY | _O_CREAT | _O_TRUNC)  w+ _O_RDWR (usually _O_RDWR | _O_CREAT | _O_TRUNC)  b _O_BINARY  t _O_TEXT  c None  n None    Example  /* FOPEN.C: This program opens files named "data"  * and "data2".It  uses fclose to close "data" and  * _fcloseall to close all remaining files.  */  #include <stdio.h>  FILE *stream, *stream2;  void main( void ) {    int numclosed;     /* Open for read (will fail if file "data" does not exist) */    if( (stream  = fopen( "data", "r" )) == NULL )       printf( "The file 'data' was not opened\n" );    else       printf( "The file 'data' was opened\n" );     /* Open for write */    if( (stream2 = fopen( "data2", "w+" )) == NULL )       printf( "The file 'data2' was not opened\n" );    else       printf( "The file 'data2' was opened\n" );     /* Close stream */    if( fclose( stream ) )       printf( "The file 'data' was not closed\n" );     /* All other files are closed: */    numclosed = _fcloseall( );    printf( "Number of files closed by _fcloseall: %u\n", numclosed ); }   Output  The file 'data' was opened The file 'data2' was opened Number of files closed by _fcloseall: 1   Stream I/O Routines  See Also   fclose, _fdopen, ferror, _fileno, freopen, _open, _setmode


Question: 链栈

#include <stdio.h> #include <stdlib.h>  #define ERROR 0 #define OK 1  int n=0; typedef int ElemType;  typedef struct stack {     ElemType data;     struct stack *next; }linkstack;  linkstack *initial(linkstack **top) {     /* 无意义的申请空间，申请的空间没了*/     //*top = (linkstack *)malloc(sizeof(linkstack));     *top = NULL;     return *top; }  int Empty(linkstack *top) {     return(top==NULL ? OK:ERROR); }  int push(linkstack **top) {     linkstack *p;     p = (linkstack *)malloc(sizeof(linkstack ));     if(!p)         return ERROR;     printf("请输入进栈的整数：");     scanf("%d",&p->data);     p->next = *top;     *top = p;     n++;     return OK; }  int pop(linkstack **top) {     linkstack *p;     p = *top;     if(p == NULL)         return ERROR;     printf("出栈元素为%d",p->data);     *top = (*top)->next;     free(p);     n--;     return OK; }  void print(linkstack *top) {     linkstack *p;     p=top;     if(p==NULL)         printf("栈为空");     else     {         for(p=top;p!=NULL;p=p->next)         {             printf("%d ",p->data);         }     }     putchar(10); }  int main(void) {     int i;      linkstack *top;      printf("1.链栈初始化\n2.链栈判空\n3.链栈进栈\n4.链栈出栈\n5.遍历\n\n");     while(scanf("%d",&i)==1)     {         switch(i)         {             case 1:top = initial(&top);                    printf("初始化成功");                    break;             case 2:if(Empty(top))                        printf("链栈为空\n");                    else                        printf("链栈不为空\n");                    break;             case 3:                    if(push(&top))                        printf("进栈成功\n");                    else                        printf("jinzhan shibai\n");                    break;             case 4:if(pop(&top))                        printf("出栈成功\n");                    else                        printf("栈为空\n");                    break;             case 5:                    print(top);                    break;         }         printf("\n");     } }  栈的初始化有问题，申请的空间没有使用就找不到了，内存泄露了。 栈的入栈出栈都需要传二重指针进去，不然不能得到入栈后的新的链表头，出栈不能得到新的链表头

linkstack *initial(linkstack *top) {      top=(linkstack *)malloc(sizeof(linkstack));     top->next = NULL;     return top; }  int Empty(linkstack *top) {     return(top->next ==NULL?OK:ERROR); }

linkstack *initial(linkstack *top) {      top=(linkstack *)malloc(sizeof(linkstack));     top=NULL;     return top; }  int Empty(linkstack *top) {     return(top==NULL?OK:ERROR); }   这两段错了


Question: C语言   关于int类型输入错误的问题

输入部分改成这样试试   char a[1024] = ""; while (scanf("%s",&a)<=0)     {         printf("输入错误，请重新选择\n");         fflush(stdin);         CDtwo();     }        n = a[0] - '0';         if (n!=1&&n!=2&&n!=3&&n!=4&&n!=5)             {                 printf("输入错误，请重新选择\n");                    CDtwo();             } }

CDone();                           //返回该函数开头 这句可不是回到函数开头，这是递归，是在函数的基础上再调用自身。学名叫做递归；  CDtwo(); 这地方也是，是递归；  为什么回到函数开头呢，直接继续输入就好了。

递归函数CDone没有退出条件吗

可以编写一个防止暴力输入的函数，以字符串接收所输入的内容，判断字符数，当大于1时提示错误，当等于1时，利用acsii码值判断是否为1活其他数字，不符合条件时提示错误，符合时转换为int并返回。

仅供参考：#include <stdio.h> #include <string.h> char s[80]; int i; char c; int main() {     while (1) {         printf("Input a integer:");fflush(stdout);         rewind(stdin);         fgets(s,80,stdin);         if (strlen(s)>10) {             printf("Input too long(>9)!\n");             continue;         }         if (2==sscanf(s,"%d%c",&i,&c)) {             if ('\n'==c) {                 printf("%d is a integer.\n",i);                 break;             }         }         if ('\n'==s[strlen(s)-1]) s[strlen(s)-1]=0;         printf("\"%s\" is NOT a integer!\n",s);     }     return 0; }


Question: C语言问题请教

首先strstr是字符串操作的函数，因此传入strstr的参数需要时字符串； char a[] = {0x31,0x32,0x33,0x34,0x35,0x36,0x37};   char b[] = {0x35,0x36}; 这两个只能算是字符数组，不是字符串。因为字符数组里没有字符串结束的标记'\0'。

strstr是针对两个字符串，你要区分字符串和字符数组

数组后面编译器不应该默认加结束符吗？那第三个程序为什么能运行成功？

第一个程序字符串没有结束符0,,,会越界访问,导致错误. 应该这样  char a[] = {0x31,0x32,0x33,0x34,0x35,0x36,0x37, 0};   char b[] = {0x35,0x36, 0};

C:\Program Files\Microsoft Visual Studio 10.0\VC\crt\src\strstr.c /*** *strstr.c - search for one string inside another * *       Copyright (c) Microsoft Corporation. All rights reserved. * *Purpose: *       defines strstr() - search for one string inside another * *******************************************************************************/  #include <cruntime.h> #include <string.h>  /*** *char *strstr(string1, string2) - search for string2 in string1 * *Purpose: *       finds the first occurrence of string2 in string1 * *Entry: *       char *string1 - string to search in *       char *string2 - string to search for * *Exit: *       returns a pointer to the first occurrence of string2 in *       string1, or NULL if string2 does not occur in string1 * *Uses: * *Exceptions: * *******************************************************************************/  char * __cdecl strstr (         const char * str1,         const char * str2         ) {         char *cp = (char *) str1;         char *s1, *s2;          if ( !*str2 )             return((char *)str1);          while (*cp)         {                 s1 = cp;                 s2 = (char *) str2;                  while ( *s1 && *s2 && !(*s1-*s2) )                         s1++, s2++;                  if (!*s2)                         return(cp);                  cp++;         }          return(NULL);  }


Question: 关于C Primer plus递归例题的理解

虽然是执行同一个函数，每次函数中的n是不同的变量，而不是同一个。其次，递归完之后，还会回到上一层函数继续执行后面代码，所以还会继续输出。具体情况建议楼主单步跟踪程序运行，观察代码执行流程及变量变化情况，很容易明白的。

“给定一个小点的输入，完整单步跟踪(同时按Alt+7键查看Call Stack里面从上到下列出的对应从里层到外层的函数调用历史)一遍。”是理解递归函数工作原理的不二法门！ 递归函数关注以下几个因素 ·退出条件 ·参数有哪些 ·返回值是什么 ·局部变量有哪些 ·全局变量有哪些 ·何时输出 ·会不会导致堆栈溢出

void UpAndDown (int n) {     printf("Level %d: n location %p\n" , n, &n);     if (n < 4)         UpAndDown(n+1);     printf("LEVEL %d: n location %p\n" , n, &n); }   注意第二个输出是在UpAndDown(n+1)；之后运行的。n显示递增，这个是第一个输出printf打印的。然后又递减，这个是第二个printf输出的。 为什么会这样输出，原因就是递归。递归是再上一个函数（其实也是其本身）没释放就会申请自身的函数栈空间，然后进入函数栈。当n>=4时，就会输出第二个printf，然后进入n=3时的函数栈（因为n为3的函数栈没释放），然后在n=3是的位置继续向后运行，因此打印第二条printf内容，同理n=3时函数栈释放，进入n=2时的函数栈，继续执行第二条printf，直到运行到初始化的函数，即n= 1时。最后打印n=1时的printf，并释放空间，自此函数递归结束。

减少是因为递归函数回归了上一层！

代码块的错误，if后面用大括号包起来


Question: C关于最小公倍数最大公约数关于小程序错误求教

#include<stdio.h>  #include<math.h>  int main() {     int a,b,n,i;     int m;      scanf("%d%d",&a,&b);     n = (a<b)?a:b;      for(i = n;i >= 1; i--) {         if(a % i == 0 && b % i == 0) {             printf("最大公约数为： %d\n",i);             break;         }     }      m = (a*b)/i;      printf("最大公倍数为： %d\n",m);          return 0; } 就你的代码而言主要是语法错误，逻辑咱没问题。

代码没问题，只是你中英文符号不对，导致编译不过去

#include<stdio.h> int gcd(int p,int q); int main(int argc,char **argv){ 	int q,p; 	scanf("%d%d",&p,&q); 	printf("最大公约数是%d",gcd(p,q)); 	return 0; }  int gcd(int p,int q){ 	return q>0?gcd(q,p%q):p; }


Question: 条件运算符不能按理想的比较大小，是有什么地方忽略了吗，求指教。谢谢啦

若返回值与函数类型不同  默认会做类型强制转换的。

#include<stdio.h>  float max(float x,float y) {     float z ;     z = x>y?x:y;     return (z); } int main() {     float a ,b, c;      scanf("%f,%f",&a,&b);     c=max(a,b);     printf("%f\n",c);     return 0; } 参考一下吧  float转int会去掉小数部分；

http://edu.csdn.net/course/detail/2344 C语言指针与汇编内存地址-一.代码要素

谢谢你们的解答，这道题我不理解的原因时条件运算符当x>y为真时执行第二条语句x，为假时执行y。我再执行时会出现不管为真为假都执行第二条语句x。而不是你们所说的强制转换。

你的max函数都没类型的 你返回float 还用int 接收....


Question: c用module32first和module32next怎么不成功，getlasterror返回错误18

TH32CS_SNAPPROCESS是遍历进程，如果你要遍历模块用TH32CS_SNAPMODULE或TH32CS_GETALLMODS


Question: 来个大神解惑下这个6174问题怎么有误？

小白第一次来发帖，受教了。。

#include<stdio.h> //#include <unistd.h>  typedef void (*pfunc)(int *, int *);  static void swap(int *a, int *b) {     int tmp;         tmp = *a;         *a  = *b;         *b  = tmp; }  void asc_sort(int *a, int *b) {    if (*a > *b)        swap(a, b); }  void des_sort(int *a, int *b) {    if (*a < *b)        swap(a, b); }  void bubble_sort(int *arr, int size, pfunc sort) {     int i, j;      for (i = 0; i < size; i++)         for (j = 0; j < size - i - 1; j++)             sort(&arr[j], &arr[j+1]); }  int get_val(int *arr, int size) {     int i, val = 0;     for (i = 0; i < size; i++) {         val = val * 10;         val += arr[i];     }      return val; }  void get_arr(int *arr, int size, int key) {     int n = key, i;      for (i = 0; i < size; i++) {         arr[i] = n % 10;         n /= 10;     } }  int check_digit(int *arr, int size, int n) {     get_arr(arr, size, n);     bubble_sort(arr, size, des_sort);     if (arr[0] == arr[1]         || arr[1] == arr[2] || arr[2] == arr[3])         return 0;     return 1; }  int main(void) {     int n, arr[4], n1, n2;      while (scanf("%d", &n)) {         if (n < 1000 || n > 9999) {             printf("Input error, please continue!\n");             continue;         }         if (check_digit(arr, 4, n))             break;         else             printf("Input error, please continue!\n");     }      do {         get_arr(arr, 4, n);         bubble_sort(arr, 4, des_sort);         n1 = get_val(arr, 4);         bubble_sort(arr, 4, asc_sort);         n2 = get_val(arr, 4);         n = n1 - n2;         printf("4%d - %4d = %4d\n", n1, n2, n);     } while (n != 6174);       return 0; }  我的自定义函数比较多，并且用到了函数指针。冒泡排序等

#include<stdio.h> #include <unistd.h> #if 0 int main(int argc, const char *argv[]) {     int a[4] = {0};     int i,j,k,max,min,n,temp1,temp2;     printf("please input a four number\n");     scanf("%d",&n);     do     {         for(i=0;i<4;i++)         {             a[i]=n%10;             n/=10;         }         for(j=0;j<4;j++)         {             if(a[j]<a[j+1])             {                 temp1=a[j];                 a[j]=a[j+1];                 a[j+1]=temp1;             }         }         max=a[0]*1000+a[1]*100+a[2]*10+a[3];         for(k=0;k<4;k++)         {             if(a[k]>a[k+1])             {                 temp2=a[k];                 a[k]=a[k+1];                 a[k+1]=temp2;             }         }         min=a[3]*1000+a[2]*100+a[1]*10+a[0];         n=max-min;         printf("%d-%d=%d",max,min,n);     }while(n!=6174&&n!=0);     return 0; } #endif typedef void (*pfunc)(int *, int *);  static void swap(int *a, int *b) {     int tmp;         tmp = *a;         *a  = *b;         *b  = tmp; }  void asc_sort(int *a, int *b) {    if (*a > *b)        swap(a, b); }  void des_sort(int *a, int *b) {    if (*a < *b)        swap(a, b); }  void bubble_sort(int *arr, int size, pfunc sort) {     int i, j;      for (i = 0; i < size; i++)         for (j = 0; j < size - i - 1; j++)             sort(&arr[j], &arr[j+1]); }  int get_val(int *arr, int size) {     int i, val = 0;     for (i = 0; i < size; i++) {         val = val * 10;         val += arr[i];     }      return val; }  void get_arr(int *arr, int size, int key) {     int n = key, i;      for (i = 0; i < size; i++) {         arr[i] = n % 10;         n /= 10;     } }  int check_digit(int *arr, int size, int n) {     get_arr(arr, size, n);     bubble_sort(arr, size, des_sort);     if (arr[0] == arr[1]         || arr[1] == arr[2] || arr[2] == arr[3])         return 0;     return 1; }  int main(void) {     int n, arr[4], n1, n2;      while (scanf("%d", &n)) {         if (n < 1000 || n > 9999) {             printf("Input error, please continue!\n");             continue;         }         if (check_digit(arr, 4, n))             break;         else             printf("Input error, please continue!\n");     }      do {         get_arr(arr, 4, n);         bubble_sort(arr, 4, des_sort);         n1 = get_val(arr, 4);         bubble_sort(arr, 4, asc_sort);         n2 = get_val(arr, 4);         n = n1 - n2;         printf("%d - %d = %d\n", n1, n2, n);         sleep(1);     } while (n != 6174);       return 0; } 参考一下～

代码功能归根结底不是别人帮自己看或讲解或注释出来的；而是被自己静下心来花足够长的时间和精力亲自动手单步或设断点或对执行到某步获得的中间结果显示或写到日志文件中一步一步分析出来的。 提醒：再牛×的老师也无法代替学生自己领悟和上厕所！ 单步调试和设断点调试（VS IDE中编译连接通过以后，按F10或F11键单步执行，按Shift+F11退出当前函数；在某行按F9设断点后按F5执行停在该断点处。）是程序员必须掌握的技能之一。


Question: 音频处理算法

引用 1 楼 zhao4zhong1 的回复:bass库。 非常感谢，请问大神有过音频信号采集、处理经验吗？

bass库。


Question: 关于函数指针的问题，新手跪求啊！

《牛肉干》 C语言上机课，某女同学偷偷吃起牛肉干。 有一粒牛肉干掉到了键盘上，卡在7和8键之间。 女同学就在键盘上抠啊、抠啊、抠啊…… 程序里一行代码变成这个样子： int *pa=&*&*&*&*&*&*&*&*&*&*&*&*&*&*&*&*&*&*&*&*&*&*&*&a; 后来的结局是 ————程序顺利通过编译，运行结果正确！

1、两种方法效果是一样的，如果你想，甚至可以写成：（*****p）（a,b）  2、确实需要定义成：（*p）（int a，int b），C语言里允许这样的隐匿转换，在C++里则会报错

仅供参考：#include <stdio.h> double A[300][100]; double valuex[300]; double valuey[300]; int i; double fun00(double x,double y) {return x  +   y  ;}; double fun01(double x,double y) {return x*x+ 3*y  ;}; double fun02(double x,double y) {return x  + 2*y*x;}; //...  fun03(double x,double y) {return ...+...   ;}; //... //...  fun98(double x,double y) {return ...+...   ;}; double fun99(double x,double y) {return x/2+20*y  ;}; double (*funNN[100])(double,double)={     fun00,     fun01,     fun02, //  fun03, //  ... //  fun98,     fun99, }; int main() {     double x,y;     int f,FN;      for (i=0;i<300;i++) {         valuex[i]=(double)i;         valuey[i]=(double)i;     }     FN=3;     for (i=0;i<300;i++) {          x=valuex[i];          y=valuey[i];          for (f=0;f<FN;f++) A[i][f]=funNN[f](x,y);     }     for (i=0;i<3;i++) {         for (f=0;f<FN;f++) printf("%lg ",A[i][f]);         printf("\n");     }     return 0; } //0 0 0 //2 4 3 //4 10 10

C语言里面int (*p)()表示参数个数以及类型未知，不建议这么写， （*p）(a, b)和（******p）(a, b)和p(a, b)效果都是一样的  这里标准的定义是int (*p)(int, int)  帮你解释了你又不看

第一个问题。既然定义了函数指针 int (*p)(); 并且 p=max。。为什么有变量指针调用函数的时候不是p（a,b）而是（*p）（a,b）呢？？ 这个问题谁能给出详细的解释么？

函数指针定义时需要确定参数的个数，类型已经返回值的类型。这样函数指针才能和对应的函数匹配。 若函数指针比较多，参数个数，类型以及返回值不确定就会有问题。

#include <stdio.h>  int my_max(int a, int b);  int main(void) {     int (*pfunc)(int, int);      pfunc = my_max;      printf("%d\n", pfunc(2, 3));      return 0; }  int my_max(int a, int b) {     return (a > b ? a : b); } 参考一下吧；

//char (*(*x[3])())[5];//x是什么类型的变量? // //分析C语言声明，关键是搞清楚这个变量是个什么东西（函数、指针、数组）， //是函数那么剩下的就是他的参数和返回值， //是指针那剩下部分是说明他指向什么， //是数组剩下的部分就是说明数组的成员是什么类型。 //解析C语言声明规则： //从左侧第一个标识符开始，按照优先级进行结合。*表示是..的指针，const表示只读的，volatile表示可变的，[]表示是数组，()表示是函数。 // //x和[3]结合说明是一个大小为3的数组，该数组的每个元素为一类指针，该类指针指向一类函数，该类函数无参数，返回一类指针，该类指针指向一个大小为5的char型数组 #include <stdio.h> #include <typeinfo.h> char num[5]; char (*x00())[5] {     return # } int main() {     char (*(*x[3])())[5];//是个数组，大小为3     char (*(*x0  )())[5];//数组的元素，是个函数指针     char (*( x00 )())[5];//函数原型，参数为空，返回值为指针     char (*  x000   )[5];//返回值      x0 = x00;     x[0] = x0;     x[1] = x0;     x[2] = x0;     printf("typeid(x).name() is %s\n",typeid(x).name());     return 0; } //typeid(x).name() is char (* (__cdecl**)(void))[5]

这里标准的定义是int (*p)(int, int)

顶！！求解啊！

正好我也在找这个问题，不懂帮顶，一起学习


Question: 求解C语言赋值运算符与逗号运算符问题

b || c是判断表达式，若b为非0，则该逗号里的表示为1，若b为0，但是c为非0，则该表示的值为1，若b和c都为0，则表达式的值为0.

其实这个是逗号运算符的问题，逗号运算符是将最后一个表达式的值赋值给e

逗号运算符优先级最低

先把运算符的优先级捞出来，按照优先级高低做运算 b||c的优先级，跟逗号的优先级，谁高谁低？

e = (a + b >d,b || c,c++,++d,3+2); e = ( ( (a + b) >d),  (b || c) ,  (c++),  (++d) ,  (3+2) ); 这个逗号运算符比较好理解，e最后就是3+2的值，b||c也起不了什么作用，因为逗号运算符也不会关心之前的逻辑运算结果导致“短路”，这个应该是题目拿来迷惑的，楼主的意志要坚定 int a = 3,b = 2,c = 4,d = 8,e = 0; a += b * c;    a = 11 b-= c / b;      b = 0 d%= a;         d = 8


Question: 关于getchar()输入的问题

楼主，换行是自己敲得吗，为啥没有回车？你的环境好神奇。 就像你的代码写的，sssa，中的a肯定不会打印出来，因为for循环结束的时候，c是‘a’ sssas的时候，for循环结束，c还是'a'，后面又输入了一个's'

引用 3 楼 qq_36177617 的回复:因为输入sssa时，遇到了最后的a则不再打印，此时'a'已经存在了for循环的c里，因此会打印sss 后面c = getchar();接收到的是换行符'\n'，因此换行符会将最后的'a'覆盖了。因此最后打出c是换行。  ___________________________________________________________________________________ 这个我明白呢，我的意思是sssas时，换行符为什么没有了，直接显示的是ssss,而不是sss换行s。 因为'a'后面的s是被第二个getchar()接收了赋值给c，因此第二个getchar();后输出的还是s 那么回车符在哪呢？还是输入缓存里。程序运行完输入缓存清空。


Question: 求解图片的意思，不懂C语言

其实就是strcat的实现思路，找到s1的结尾字符，然后把s2的内容复制给s1

把字符串s2拼到字符串s1的后面。 第一个while循环找到字符串s1结束时的下标，第二个while是把字符串s2   从刚找到的下标位置    逐个逐个字符的往后写，最后加一个字符串结束标志‘\0’。 i++相当于i=i+1; s1[i++] = s2[j++]相当于{s[i] = s[j];i=i+1;j=j+1;}

代码功能归根结底不是别人帮自己看或讲解或注释出来的；而是被自己静下心来花足够长的时间和精力亲自动手单步或设断点或对执行到某步获得的中间结果显示或写到日志文件中一步一步分析出来的。 提醒：再牛×的老师也无法代替学生自己领悟和上厕所！ 单步调试和设断点调试（VS IDE中编译连接通过以后，按F10或F11键单步执行，按Shift+F11退出当前函数；在某行按F9设断点后按F5执行停在该断点处。）是程序员必须掌握的技能之一。

j++ ; // 先运算，再增加， 如果 j = 1; a = j++; 则a = 1;  ++j; // 先增加再运算，如果j = 1; a = ++j; 则a = 2;

输入的字符串系统会自动在最后加个\0，所以第一个for是找到s1的末尾，第二个for是把s2加到s1后面，然后再加个\0作为字符串结尾

自己运行一下 或者在纸上按以上算法写一下

合并两个字符串，类似strcat的功能。

引用 4 楼 自信男孩的回复:功能是连接两个字符串，第一个while循环是找到第一个字符串的末尾，i是末尾（'\0'）的偏移。第二个循环是将第二个字符串加到第一个字符串的末尾，是一个字符一个字符赋值的。s[i] = '\0‘是给连接后的字符串加'\0'，没有'\0'不算是字符串。 请问一下第二个while中i和j是先加一再进行赋值，还是赋值之后再加一再去判定？

strcpy字符串复制功能，第一个while是将数组置空，第二个是循环赋值。最后把 '\0' 加到字符串末尾。


Question: 结构体变量的初始化

#include <stdio.h>  struct student {     int num;   char name[20];   char sex;    int age;    float score;    char addr[20]; }stu = {0};  int main(void) {     printf("stu.age = %d, stu.score = %f\n", stu.age, stu.score);     return 0; } 初始化也可以单独操作； #include <stdio.h>  struct student {     int num;   char name[20];   char sex;    int age;    float score;    char addr[20]; }stu = {0};  int main(void) {     printf("stu.age = %d, stu.score = %f\n", stu.age, stu.score);     stu.age=0;     stu.score=0;     return 0; }

这样可以的。


Question: 自定义的结构体问题

引用 9 楼 shihengzhen101 的回复:[quote=引用 8 楼 runningfatty 的回复:] 刚刚已经成功的找到原因了，就是因为源代码中出现的if语句后面的那一行代码没有加大括号造成的 心态炸了。。。。没听说过这东西还会报错的 有没有大神能给解释下。。。。 能跑的那台电脑上也没有加过大括号就能正常用，这边为什么就不行呢。。。。 我等待大神出现[/quote]  同等，我也很好奇

引用 8 楼 runningfatty 的回复:刚刚已经成功的找到原因了，就是因为源代码中出现的if语句后面的那一行代码没有加大括号造成的 心态炸了。。。。没听说过这东西还会报错的 有没有大神能给解释下。。。。 能跑的那台电脑上也没有加过大括号就能正常用，这边为什么就不行呢。。。。 我等待大神出现

偶遇到类似问题都是用 “每次用/*...*/注释掉不同部分再重新编译，直到定位到具体语法出错的位置。” 的方法解决的。

引用 6 楼 shihengzhen101 的回复:是不是添加应有的包含文件所在路径，那个能跑的电脑是你配置的吗 所有的电脑都是我配置的 因为我需要GPU并行运算，所以需要在这台电脑上跑起来， 但是到目前为止只有一台电脑成功的编译啦，其他的都是出现同样的问题，也不知道到底是哪里的错误，所有的配置都是按步骤一步一步来的

是不是添加应有的包含文件所在路径，那个能跑的电脑是你配置的吗

不要沉啊。。。

在设置里面，把预处理头文件去掉试试？

引用 1 楼 cfjtaishan 的回复:找一下im定义的地方，这个不识别，是不是这个定义没有在引用的地方include头文件呢   所有的源代码中都正常的包含了所需的头文件，而且程序在另一台电脑上是能够正常跑的，新建了工程测试结构体也是正常的，就是在这里不知道为什么出错。 所有的错误都是这种，有了正常的定义，但是都无法进行正常的初始化。 这个程序里面有c代码和cuda的代码，会不会是因为这里的原因造成的？

重构一下项目吧


Question: 【C语言基础：疑问】

明白了，谢谢大家～～(´･ω･`)

status=scanf("%1d",&num); 都是%1d中的1惹的祸，因为输入个是1d，所以只得到一个一位数，10是两位数。 去掉1，正常运行。

引用 4 楼 iloveyou418 的回复:%1d。。。这个你输入10的话它会当成两次输入依次是1，0，所以会出现这个现象。。。  正解

你判断的是scanf的返回值  返回值的定义如下： Return Value  These functions return the number of input items successfully matched and assigned, which can be fewer than provided for, or even zero in the event of an early matching failure.  The value EOF is returned if the end of input is reached before either the first successful conversion or a matching failure occurs. EOF is also returned if a read error occurs, in which case the error indicator for the stream (see ferror(3)) is set, and errno is set indicate the error.  理解这段话就好了！

其实我对这个while的循环条件判断耶不是很明白，为何是status==1?只要我第二次输入的num！=1，那不就跳出循环了吗？这样的话又为什么会输出1～9求和的正确结果呢？？（以上代码，出自C Primer Plus）

编译器是CLion


Question: 求解两道C语言问题

\x11是一个转义字符，代表的是十六进制， \101是八进制。

先说第二个t = (double)k;这个赋值操作是现将k的值转成double类型，然后赋值给t。这个操作注意是k的值，即内存里存放的值，而不是k转double。因此k还是int类型。k的类型是由其定义时决定的，中间不能改变其类型。  第一个输出字符长度，个人建议先运行一下strlen()，看输出结果是多少，然后分析一下; 该字符串中有两个转义字符\，第一个\x说明后面11是十六进制数。'\101'输出值是65，即是8进制数。 因此这两个转义后的只能算是2个字符，再加上3个字母，总共是5个字符长度。


Question: 关于C primer Plus 第七章一个例题

1. 首先假定它是一个素数，所以设置标志位为真， 假如找到能够整除它的因子，证明它不是素数，就可以把标志位设置为假了  2.  程序是用div来试除待测试的数 if (num % div == 0) 表示div能够整除num，相当于说num有因子，不是素数  反过来，假如num是一个素数，就不可能找到一个数能够整除它。 因此假如num是一个素数，就不会执行这个if语句


Question: strcpy失败问题

#include <stdio.h> #include <string.h>  int main() {     char str[12] = { 0 };      strcpy(str,"abcd");     strcpy(str + 4, "1234");      puts(str);     system("pause");     return 0; } 出现这样的错误是随机的，原因是数组越界，数组越界是未定义行为，可能会导致你的这种现象，也可能正常输出；  建议将str长度定义更大写，保证能够接收要拷贝的字符，另外加一个'\0'；如果用循环赋值，不用考虑'\0'，但是楼主用的是strcpy，这个是字符串拷贝函数，仅用于字符串拷贝用。

引用 2 楼 Tianzez 的回复:但我这不是字符数组吗？数组也要加‘\0’结尾？strcpy会在最后自动补\0，所以越界。

但我这不是字符数组吗？数组也要加‘\0’结尾？

字符串长度不够，要给\0留一个位置


Question: C语言写题目遇到一点问题，求助！

引用 3 楼 wkr145 的回复:首先谢谢，第一个题解决了，但是第二个题有点问题，改成   long a 之后如图。 #include <stdio.h>  long Jie(int n);   int main()  {    int n;    long result;    printf("Please input the number u want:");    scanf_s("%d", &n);    result = Jie(n);    return 0;  }  long Jie(int n) {    int i, j;    long a;    a = 1;    for (i = 1;i <= n;i++)    {       //for (j = 1;j <= i;j++)       {          a *= i;       }       printf("%d! = %ld\n",i, a);    }    return 0; }

代码功能归根结底不是别人帮自己看或讲解或注释出来的；而是被自己静下心来花足够长的时间和精力亲自动手单步或设断点或对执行到某步获得的中间结果显示或写到日志文件中一步一步分析出来的。 提醒：再牛×的老师也无法代替学生自己领悟和上厕所！ 单步调试和设断点调试（VS IDE中编译连接通过以后，按F10或F11键单步执行，按Shift+F11退出当前函数；在某行按F9设断点后按F5执行停在该断点处。）是程序员必须掌握的技能之一。

求阶乘不是只需要第一个for语句吗？第二个不是有多吗？？？？

首先谢谢，第一个题解决了，但是第二个题有点问题，改成   long a 之后如图。

double 类型输入用%lf，输出用%f %lf都行。不过你为什么要用double类型，明明计算结果和返回值都是int 类型啊

第一题 输出语句的数据类型不对了两种改法： 一种是把 double number; 改成 long number;  另一种是把printf("This  you have :  %ld", number); 改成 printf("This  you have :  %f", number); //输出浮点型数  第二题 也是输出语句的数据类型不对了两种改法： 一种是把 double a; 改成 long a； 另一种是把printf("%d! = %ld\n",i, a);改成 printf("%d! = %f\n",i, a);//输出浮点型数

引用 4 楼 cfjtaishan 的回复:第一个改一下数据类型就可以。将double改成long或者改一下输出格式用%.0lf输出。 第二个是改一下输出格式%.0lf;  这两个问题主要是浮点数和整型数在内存里的存放格式不一样。因此应该用 应该用对应的格式输出对应的数据。


Question: C语言将字符写入文件失败是什么原因

积分少啊。可怜

Administrator的用户目录，权限够吗

引用 1楼jiht594 的回复:路径存在吗？ 换个路径试试确定路径正确……

如果程序正常运行，不应该不创建文件并写文件； 文件如果没打开失败（程序里有提示若打开失败），建议到对应目录下寻找文件；  程序没发现问题；建议若文件打开成功加一条打印信息，文件打开成功；这样保证文件能够正常打开（创建）

路径存在吗？ 换个路径试试

fflush


Question: 请问：free释放指针为什么会出错

是 int *temp =(int*) malloc(len * sizeof(int)); 这里要这样才可以，谢谢。

应该是访问堆内在越界了，导致堆破坏，从而在释放时出错

n2是什么？  printf("%d  %d\n",n1,n2);	   malloc大小错误  int *temp =(int*) malloc(len * sizeof(int));

看代码貌似没错，除非temp的值为空，或被踩，但这种情况应该在前面就出错。未见得是free的错误，你把temp换到栈空间（使用局部变量temp[64]）看一下，如果还出错就不是指针释放的问题，可能栈空间溢出。建议你把宕机时的调用栈信息贴出来。


Question: 新人求助

引用 1 楼 user-2 的回复:#include<stdio.h> int F(int x) { int m = 0; if(x == 1) 	return ++m; else if(x % 2 == 0) 	m = 1 + F(x/2); else 	m = 1 + F(3*x + 1);  return m;  }   int main(void){ int x; scanf("%d",&x); printf("%d",F(x)); return 0; }  高手！这是什么算法啊，你是怎么抽象出来的？


Question: C语言中一个指针问题

引用 8 楼 u011261943 的回复:[quote=引用 7 楼 cfjtaishan 的回复:] [quote=引用 3 楼 u011261943 的回复:] cArray 是在函数 testX()内声明的变量，当 testX()执行完之后， cArray就会被释放。 准确地说，在将cArray的所指向的地址传给p之后，整个cArray数组就被释放了。 此时，p就是一个野指针，它指向一段垃圾内存。 p不是野指针，而是已经固定的指针。内存释放但不会对p做任何修改；p指向的还是已经释放的区域。  对于野指针的定义，建议还需要看一下概念；[/quote]  指向一个已删除的对象或未申请访问受限内存区域的指针。cArray这里属于 指向一个已删除的对象。[/quote]  sorry，说错了，不是cArray，  p属于指向一个已删除的对象的情况。

引用 7 楼 cfjtaishan 的回复:[quote=引用 3 楼 u011261943 的回复:] cArray 是在函数 testX()内声明的变量，当 testX()执行完之后， cArray就会被释放。 准确地说，在将cArray的所指向的地址传给p之后，整个cArray数组就被释放了。 此时，p就是一个野指针，它指向一段垃圾内存。 p不是野指针，而是已经固定的指针。内存释放但不会对p做任何修改；p指向的还是已经释放的区域。  对于野指针的定义，建议还需要看一下概念；[/quote]  指向一个已删除的对象或未申请访问受限内存区域的指针。cArray这里属于 指向一个已删除的对象。

引用 3 楼 u011261943 的回复:cArray 是在函数 testX()内声明的变量，当 testX()执行完之后， cArray就会被释放。 准确地说，在将cArray的所指向的地址传给p之后，整个cArray数组就被释放了。 此时，p就是一个野指针，它指向一段垃圾内存。 p不是野指针，而是已经固定的指针。内存释放但不会对p做任何修改；p指向的还是已经释放的区域。  对于野指针的定义，建议还需要看一下概念；

引用 1 楼 cfjtaishan 的回复:这个是经典问题了：返回局部数组；只是未定义行为。 因为局部变量数组是在栈上申请空间，函数testX调用结束后会自动被释放，因此返回局部变量数组没有意义。局部数组的生命周期是从定义开始，到函数调用结束而结束； 如果想继续使用，那么通过数组定义时加static或者数组从堆上申请空间（malloc/free），这样可以改变它的生命周期。 加static后数组是在静态数据段申请空间，生命周期是从定义开始，到程序运行结束而结束； 一个是函数运行结束而结束，一个是程序运行结束而结束； 非常感谢,通俗易懂,再次谢谢,我明白了

引用 2 楼 user-3 的回复:你的cArray是个局部变量，testX函数结束后就销毁了，这就是为什么不要返回指向局部变量的指针的原因 谢谢,我明白了

引用 3 楼 u011261943 的回复:cArray 是在函数 testX()内声明的变量，当 testX()执行完之后， cArray就会被释放。 准确地说，在将cArray的所指向的地址传给p之后，整个cArray数组就被释放了。 此时，p就是一个野指针，它指向一段垃圾内存。 谢谢,不过我没有分了,给上面的第一个回答的了,谢谢


Question: 热烈庆祝本人受关注人数即将突破14000大关！散分！！+超大文件排序源代码

Hi,老师，我现在碰到一个问题，就是如何修改拖曳文件的打开顺序，毫无头绪现在。求老师解答。 现有思路：修改HDROP指向的内存内容，但不知道如何操作。想要用PostMessage模拟WM_DROPFILES消息，但是不知怎么构造参数 帖子地址：https://bbs.csdn.net/topics/392345182  私信功能不行了，只能来这里找您了

谢谢分享，赵老师

引用 55 楼 flagoop 的回复:千万中取首，如梭，如风，如闪电

千万中取首，如梭，如风，如闪电

试试

【让窗体永远在前面】 有时候你希望某个窗体永远在前面，使用【csdn967】程序能够帮你做到！ 求你们也去关注一下me===CSDN967

好厉害，膜拜尼古拉斯·赵老师

额额额顶一个

恭喜恭喜，我也关注下大佬

引用 40 楼 zhao4zhong1 的回复:不要迷信书、考题、老师、回帖； 要迷信CPU、编译器、调试器、运行结果。 并请结合“盲人摸太阳”和“驾船出海时一定只带一个指南针。”加以理解。 任何理论、权威、传说、真理、标准、解释、想象、知识……都比不上摆在眼前的事实！赵老师说的对啊

WindowsXP，如果磁盘上有1TB的数据需要排序，但只有1GB的内存，你怎么做？

赵老师,我来看望您老人家

引用 40 楼 zhao4zhong1 的回复:不要迷信书、考题、老师、回帖； 要迷信CPU、编译器、调试器、运行结果。 并请结合“盲人摸太阳”和“驾船出海时一定只带一个指南针。”加以理解。 任何理论、权威、传说、真理、标准、解释、想象、知识……都比不上摆在眼前的事实！  路过学习，事实上也是“做到才能得到”

厉害了。一直被模仿，

还没仔细研究，不过赵老师出版，必属佳品！


Question: 键盘输入ctrl+z作用是什么？

引用 3 楼 赵4老师的回复:File: "C:\Program Files\Microsoft Visual Studio 10.0\VC\crt\src\internal.h"        69: #define CTRLZ 26        /* ctrl-z means eof for text */ File: "C:\Program Files\Microsoft Visual Studio 10.0\VC\crt\src\read.c"      277:                     if (*p == CTRLZ) {      478:                     if (*pu == CTRLZ) { File: "C:\Program Files\Microsoft Visual Studio 10.0\VC\crt\src\write.c"      494:                 else if ((_osfile(fh) & FDEV) && *(char *)buf == CTRLZ)   嗷嗷，多谢。能问下为什么ctrl+z前面有字符的时候，它就会忽略这一行ctrl+z后的字符，并且按回车也不结束输入呢？(而且出现了图里的箭头……)

引用 1 楼 自信男孩的回复:ctrl+z是Windows下输入EOF的命令。输入EOF，首先程序里需要有判断输入的是否位EOF。所以，如果输入Ctrl+z没有效果，要看程序里有没有判断EOF 建议贴出你的代码 就很简单的定义了一个字符数组，用gets()和puts()输入输出字符串，没别的了。图里最后一行是输出的。 我还了解到是不是和什么阻塞和非阻塞有关？


Question: C 指针跟数组问题求组

十分感谢 确实越界了  @ cfjtaishan @ yx777777

第三个函数里面a指向的地址已经变过了，所以直接输出会从后面开始

#include<stdio.h> #define SIZE 5  void copy_arr(double ar[], double a[], int n); void copy_ptr(double *a, double *b, int n); void copy_ptrs(double *a, double *b, double *end);  int main() { 	double source[SIZE] = { 1.1, 2.2, 3.3, 4.4, 5.5 }; 	double target1[SIZE]; 	double target2[SIZE]; 	double target3[SIZE];  	copy_arr(target1, source, SIZE);  	copy_ptr(target2, source, SIZE);  	copy_ptrs(target3, source, source + SIZE); 	return 0; }   void copy_arr(double ar[], double a[], int n) { 	int i; 	for (i = 0; i<n; i++) 		ar[i] = a[i]; 	for (i = 0; i<n; i++) 	{ 		printf("target1[%d] = %.2lf", i, ar[i]); 		printf("\n"); 	} }  void copy_ptr(double *a, double *b, int n) { 	int i; 	for (i = 0; i<n; i++) 		*(a + i) = *(b + i); 	for (i = 0; i<n; i++) 	{ 		printf("target2[%d] = %.2lf", i, a[i]); 		printf("\n"); 	} }   void copy_ptrs(double *a, double *b, double *end) { 	int i; 	double *c; 	c = a; 	while (b < end) 	{ 		*a = *b; 		b++; 		a++; 	}  	for (i = 0; i < SIZE; i++) 	{ 		printf("target3[%d] = %.2lf ", i, *(c+i)); 		printf("\n"); 	} }

void copy_ptrs(double *a, double *b,double *end) {     int i;     double *tmp = a;     while(b<end)     {         *tmp = *b;         b++;         tmp++;     }      for(i=0;i<SIZE;i++)     {         printf("target3[%d] = %.2lf ", i, *(a+i));         printf("\n");     } } 其他函数没问题，最后一个函数的问题是a已经指向数组的末尾，所以a+i已经是越界。 解决办法是赋值用一个tmp代替a，这样a还是指向目标数组的开始位置；

http://edu.csdn.net/course/detail/2344 C语言指针与汇编内存地址-一.代码要素


Question: C语言进阶求帮助

字体用错了颜色不好意思啊

#include <stdio.h> #include <stdlib.h>  struct student {     int num;     double score;     struct student *next; };  #define LEN sizeof(struct student)  struct student *create(struct student **pphead, int num) {     int i = 0;     struct student *pnew, *pcur;      while (i < num) {         pnew = (struct student *)malloc(LEN);         if (!pnew)             exit(0);         scanf("%d%lf",&pnew->num, &pnew->score);         if (!(*pphead)) {             *pphead = pnew;             pcur = *pphead;         } else {             pcur->next = pnew;             pcur = pnew;         }         i++;     }     pcur->next = NULL;      return *pphead; }   void print_link(struct student *phead) {     struct student *p = phead;      while (p) {         printf("%d %.lf\n", p->num, p->score);         p = p->next;     } }   int main() {     int n,m;     scanf("%d%d",&n,&m);              //两个链表节点数     int i=0;   #if 0     struct student *phead1, *phead2, *p;     phead1 = phead2 = NULL;      create(&phead1, m);     create(&phead2, n);      p = phead1;     while (p->next)         p = p->next;     p->next = phead2;      print_link(phead1);  #else     struct student *head1,*p1,*p2;    //定义链表一      //p2=(struct student*)malloc(100);  //动态开辟空间     p1=(struct student*)malloc(LEN);     scanf("%d%lf",&p1->num,&p1->score); //输入链表一头链表的值     head1 = p1;     p2=p1;     while(i < n-1)     {         p1=(struct student*)malloc(LEN);         scanf("%d%lf",&p1->num,&p1->score);         p2->next = p1;         p2 = p1;         i++;     }     p2->next=NULL;      i=0;     struct student *head2,*p3,*p4;           //定义链表二     p3=(struct student*)malloc(LEN);     //p4=(struct student*)malloc(100);     scanf("%d%lf",&p3->num,&p3->score);      //输入链表二头链表的值     head2 = p3;     p4 = p3;     while(i < m-1)     {         p3=(struct student*)malloc(LEN);         scanf("%d%lf",&p3->num,&p3->score);         p4->next=p3;         p4 = p3;         i++;     }     p4->next=NULL;      p2->next=head2;       //将链表二的头节点赋值给链表一尾next指针      p1 = head1;     while(p1)  //输出合并后的链表     {         printf("%d %.lf\n",p1->num,p1->score);         p1 = p1->next;     } #endif     return 0; } 参考一下吧 代码有冗余，可以将链表创建单独用一个函数实现，然后创建两个链表时直接调用自定义函数； 自定义函数详见上面的代码；仅供参考～

出错时中断下来，通过调用堆栈定位到相关位置，分析原因，必要时单步跟踪程序运行，观察变量变化情况


Question: 链表的逆序问题

#include <stdio.h> #include <malloc.h>  typedef char ElemType; typedef struct Node    {     ElemType data;     struct Node  * next; }Node, *LinkList;  void CreateFromTail(LinkList L) {     Node *r, *s;     char c;     int  flag =1;       /*设置一个标志，初值为1，当输入"$"时，flag为0，建表结束*/ 	r=L; 	while(flag)         /*循环输入表中元素值，将建立新结点s插入表尾*/     {         c=getchar();         if(c!='$')         {             s=(Node*)malloc(sizeof(Node));             s->data=c;             r->next=s;             r=s;         }         else         {             flag=0;             r->next=NULL;   /*将最后一个结点的next链域置为空，表示链表的结束*/         }     } }  void printL(LinkList L) { 	Node *r; 	r=L; 	while(r!=NULL) 	{ 		printf(" %c ",r->data); 		r=r->next; 	} }  LinkList Routine(LinkList head) { 	LinkList pre=NULL,cur=head; 	LinkList next; 	while(cur) 	{ 		next=cur->next; 		cur->next=pre; 		pre=cur; 		cur=next; 	} 	return pre; }  int main() { 	LinkList L; 	Node *s; 	char c; 	c=getchar(); 	s=(Node*)malloc(sizeof(Node));     s->data=c;     L=s; 	CreateFromTail(L); 	printL(L); 	printf(" \n "); 	L=Routine(L); 	printL(L); 	printf(" \n "); 	return 0; }

数据结构对单链表进行数据排序 http://bbs.csdn.net/topics/392201633

#include<stdio.h> #include <stdlib.h> #include<malloc.h> //#include <unistd.h>  #define len sizeof(struct Student)  struct Student{     long num;     float score;     struct Student *next; };  int n;  struct Student* creat() {     struct Student *head;     struct Student *p1,*p2;     n=0;     p1=p2=(struct Student *)malloc(len);     scanf("%ld,%f", &p1->num,&p1->score);     head = NULL;     while(p1->num != 0)     {         n=n+1;         if(n==1)         {             head=p1;         }         else         {             p2=p1;             p1=(struct Student *)malloc(len);             if (!p1)                 exit(-1);             p2->next = p1;             scanf("%ld,%f",&p1->num,&p1->score);         }     }     free(p1);    //free last node     p2->next = NULL;      return head; } void print(struct Student *head) {     struct Student *p;      p = head;      if (!p) {         printf("\nEmpty list\n");         return;     }      while(p)     {         printf("%ld %.5f\n",p->num, p->score);         p = p->next;     }      /*        if(head->next!=NULL)        {        p=head;        while(p!=NULL)        {        printf("%ld %.5f\n",p->num,p->score);        p=p->next;        }        }        else        {        printf("\nEmpty list");        }        */ } struct Student  *deundo(struct Student *head)//逆序链表 {     //struct Student *tmp;     //struct Student *p1, *p2;     struct Student *r, *s, *t;      if (!head) {         printf("\nEmpty list\n");         return NULL;     }      r = head;     s = head->next;      head->next = NULL;    /*头结点作为末节点*/     while (s) {         t = s->next;         s->next = r;         r = s;         s = t;     }     head = r;      /*     p2=NULL;     while(head!=NULL)     {         tmp=head->next;         head->next=p2;         p2=head;         head=tmp;     }     head=p2;//     */     return (head); } int main() {     struct Student *head;     //int num,num1;     //float score;     head=creat();     print(head);     head = deundo(head);     printf("\n");     print(head); } 参考一下吧； 逆序后，需要重新返回新的头结点；


Question: fseek回退覆写文件，如何结尾？EOF无效呢

引用 16 楼 zhao4zhong1 的回复:_chsize Changes the file size.  int _chsize( int handle, long size );  Routine Required Header Optional Headers Compatibility  _chsize <io.h> <errno.h> Win 95, Win NT    For additional compatibility information, see Compatibility in the Introduction.  Libraries  LIBC.LIB Single thread static library, retail version  LIBCMT.LIB Multithread static library, retail version  MSVCRT.LIB Import library for MSVCRT.DLL, retail version    Return Value  _chsize returns the value 0 if the file size is successfully changed. A return value of –1 indicates an error: errno is set to EACCES if the specified file is locked against access, to EBADF if the specified file is read-only or the handle is invalid, or to ENOSPC if no space is left on the device.  Parameters  handle  Handle referring to open file  size  New length of file in bytes  Remarks  The _chsize function extends or truncates the file associated with handle to the length specified by size. The file must be open in a mode that permits writing. Null characters ('\0') are appended if the file is extended. If the file is truncated, all data from the end of the shortened file to the original length of the file is lost.  Example   /* CHSIZE.C: This program uses _filelength to report the size  * of a file before and after modifying it with _chsize.  */  #include <io.h> #include <fcntl.h> #include <sys/types.h> #include <sys/stat.h> #include <stdio.h>  void main( void ) {    int fh, result;    unsigned int nbytes = BUFSIZ;     /* Open a file */    if( (fh = _open( "data", _O_RDWR | _O_CREAT, _S_IREAD                     | _S_IWRITE ))  != -1 )    {       printf( "File length before: %ld\n", _filelength( fh ) );       if( ( result = _chsize( fh, 329678 ) ) == 0 )          printf( "Size successfully changed\n" );       else          printf( "Problem in changing the size\n" );       printf( "File length after:  %ld\n", _filelength( fh ) );       _close( fh );    } }   Output  File length before: 0 Size successfully changed File length after:  329678     File Handling Routines  See Also   _close, _creat, _open 您好，我在C标准库中，没有找到io.h呢，这几个方法也就没发现。。。

引用 14 楼 codedoctor 的回复:[quote=引用 6 楼 sys0613 的回复:] [quote=引用 4 楼 codedoctor 的回复:] 我的意思就是直接全部重写。先直接seek到结尾，再全部装入string中进行处理，处理完之后再重新写入 当文件过大时，你这招就不太好用了[/quote]  ..你这不是抬杠吗，如果你要说大文件的话，那么你这个怎么定位输入的位置就不说了（还是得读取文件内容），而且频繁的对存储器进行读入读出是非常不好的习惯，比较好的方法就是一次读取尽可能大的数据然后进行处理再一次性的取出，而不是直接就在文件的映射区里面进行操作。 我只是针对你这个问题提出的最方便的解决方案，你要说去操作一个几个G的txt文件。那当我没有回答吧[/quote] 抱歉，还是谢谢您了

TRUNCATE Section: Linux Programmer's Manual (2) Updated: 2004-06-23  --------------------------------------------------------------------------------    NAME truncate, ftruncate - truncate a file to a specified length    SYNOPSIS #include <unistd.h>  #include <sys/types.h>  int truncate(const char *path, off_t length);  int ftruncate(int fd, off_t length);     DESCRIPTION The truncate and ftruncate functions cause the regular file named by path or referenced by fd to be truncated to a size of precisely length bytes.  If the file previously was larger than this size, the extra data is lost. If the file previously was shorter, it is extended, and the extended part reads as zero bytes.   The file pointer is not changed.   If the size changed, then the ctime and mtime fields for the file are updated, and suid and sgid mode bits may be cleared.   With ftruncate, the file must be open for writing; with truncate, the file must be writable.     RETURN VALUE On success, zero is returned. On error, -1 is returned, and errno is set appropriately.    ERRORS For truncate:  EACCES  Search permission is denied for a component of the path prefix, or the named file is not writable by the user. (See also path_resolution(2).)  EFAULT  Path points outside the process's allocated address space.  EFBIG  The argument length is larger than the maximum file size. (XSI)  EINTR  A signal was caught during execution.  EINVAL  The argument length is negative or larger than the maximum file size.  EIO  An I/O error occurred updating the inode.  EISDIR  The named file is a directory.  ELOOP  Too many symbolic links were encountered in translating the pathname.  ENAMETOOLONG  A component of a pathname exceeded 255 characters, or an entire path name exceeded 1023 characters.  ENOENT  The named file does not exist.  ENOTDIR  A component of the path prefix is not a directory.  EROFS  The named file resides on a read-only file system.  ETXTBSY  The file is a pure procedure (shared text) file that is being executed.  For ftruncate the same errors apply, but instead of things that can be wrong with path, we now have things that can be wrong with fd:   EBADF  The fd is not a valid descriptor.  EBADF or EINVAL  The fd is not open for writing.  EINVAL  The fd does not reference a regular file.     CONFORMING TO 4.4BSD, SVr4 (these function calls first appeared in BSD 4.2). POSIX 1003.1-1996 has ftruncate. POSIX 1003.1-2001 also has truncate, as an XSI extension.  SVr4 documents additional truncate error conditions EMFILE, EMULTIHP, ENFILE, ENOLINK. SVr4 documents for ftruncate an additional EAGAIN error condition.     NOTES The above description is for XSI-compliant systems. For non-XSI-compliant systems, the POSIX standard allows two behaviours for ftruncate when length exceeds the file length (note that truncate is not specified at all in such an environment): either returning an error, or extending the file. (Most Unices follow the XSI requirement.)    SEE ALSO open(2), path_resolution(2)  --------------------------------------------------------------------------------

还需要自己截断文件，参看：http://blog.csdn.net/qq_32541007/article/details/51193886

引用 1 楼 Loydia 的回复:这种情况一般会重写文件吧。另外有个函数你可以研究下：chsize 我理解这种情况应该不会重写文件，只是替换了倒数第四位和第五位，同时指针停留在倒数第三位。我就是想在倒数第三位处写入一个停止。。。不知道应该如何实现

这种情况一般会重写文件吧。另外有个函数你可以研究下：chsize

当然也是我自己没看清你的题

引用 6 楼 sys0613 的回复:[quote=引用 4 楼 codedoctor 的回复:] 我的意思就是直接全部重写。先直接seek到结尾，再全部装入string中进行处理，处理完之后再重新写入 当文件过大时，你这招就不太好用了[/quote]  ..你这不是抬杠吗，如果你要说大文件的话，那么你这个怎么定位输入的位置就不说了（还是得读取文件内容），而且频繁的对存储器进行读入读出是非常不好的习惯，比较好的方法就是一次读取尽可能大的数据然后进行处理再一次性的取出，而不是直接就在文件的映射区里面进行操作。 我只是针对你这个问题提出的最方便的解决方案，你要说去操作一个几个G的txt文件。那当我没有回答吧

我的也是纯C

引用 11 楼 Intel0011 的回复:我的是VC6.0的   [/code]  那应该不行吧，你是c++吧？我是纯c，得考虑兼容性什么的，应该不能用vc6.0

我的是VC6.0的 /*** *io.h - declarations for low-level file handling and I/O functions * *       Copyright (c) 1985-1997, Microsoft Corporation. All rights reserved. * *Purpose: *       This file contains the function declarations for the low-level *       file handling and I/O functions. * *       [Public] * ****/  #if     _MSC_VER > 1000 #pragma once #endif  #ifndef _INC_IO #define _INC_IO  #if     !defined(_WIN32) && !defined(_MAC) #error ERROR: Only Mac or Win32 targets supported! #endif   #ifdef  _MSC_VER /*  * Currently, all MS C compilers for Win32 platforms default to 8 byte  * alignment.  */ #pragma pack(push,8) #endif  /* _MSC_VER */  #ifndef _POSIX_  #ifdef  __cplusplus extern "C" { #endif    /* Define _CRTIMP */  #ifndef _CRTIMP #ifdef  _DLL #define _CRTIMP __declspec(dllimport) #else   /* ndef _DLL */ #define _CRTIMP #endif  /* _DLL */ #endif  /* _CRTIMP */   /* Define __cdecl for non-Microsoft compilers */  #if     ( !defined(_MSC_VER) && !defined(__cdecl) ) #define __cdecl #endif  /* Define _CRTAPI1 (for compatibility with the NT SDK) */  #ifndef _CRTAPI1 #if	_MSC_VER >= 800 && _M_IX86 >= 300 #define _CRTAPI1 __cdecl #else #define _CRTAPI1 #endif #endif  #ifndef _MAC #ifndef _WCHAR_T_DEFINED typedef unsigned short wchar_t; #define _WCHAR_T_DEFINED #endif #endif  /* ndef _MAC */  #ifndef _TIME_T_DEFINED typedef long time_t;            /* time value */ #define _TIME_T_DEFINED         /* avoid multiple def's of time_t */ #endif  #ifndef _FSIZE_T_DEFINED typedef unsigned long _fsize_t; /* Could be 64 bits for Win32 */ #define _FSIZE_T_DEFINED #endif  #ifndef _MAC  #ifndef _FINDDATA_T_DEFINED  struct _finddata_t {     unsigned    attrib;     time_t      time_create;    /* -1 for FAT file systems */     time_t      time_access;    /* -1 for FAT file systems */     time_t      time_write;     _fsize_t    size;     char        name[260]; };  #if     _INTEGRAL_MAX_BITS >= 64 struct _finddatai64_t {     unsigned    attrib;     time_t      time_create;    /* -1 for FAT file systems */     time_t      time_access;    /* -1 for FAT file systems */     time_t      time_write;     __int64     size;     char        name[260]; }; #endif  #define _FINDDATA_T_DEFINED #endif  #ifndef _WFINDDATA_T_DEFINED  struct _wfinddata_t {     unsigned    attrib;     time_t      time_create;    /* -1 for FAT file systems */     time_t      time_access;    /* -1 for FAT file systems */     time_t      time_write;     _fsize_t    size;     wchar_t     name[260]; };  #if     _INTEGRAL_MAX_BITS >= 64 struct _wfinddatai64_t {     unsigned    attrib;     time_t      time_create;    /* -1 for FAT file systems */     time_t      time_access;    /* -1 for FAT file systems */     time_t      time_write;     __int64     size;     wchar_t     name[260]; }; #endif  #define _WFINDDATA_T_DEFINED #endif  /* File attribute constants for _findfirst() */  #define _A_NORMAL       0x00    /* Normal file - No read/write restrictions */ #define _A_RDONLY       0x01    /* Read only file */ #define _A_HIDDEN       0x02    /* Hidden file */ #define _A_SYSTEM       0x04    /* System file */ #define _A_SUBDIR       0x10    /* Subdirectory */ #define _A_ARCH         0x20    /* Archive file */  #endif  /* ndef _MAC */  /* function prototypes */  _CRTIMP int __cdecl _access(const char *, int); _CRTIMP int __cdecl _chmod(const char *, int); _CRTIMP int __cdecl _chsize(int, long); _CRTIMP int __cdecl _close(int); _CRTIMP int __cdecl _commit(int); _CRTIMP int __cdecl _creat(const char *, int); _CRTIMP int __cdecl _dup(int); _CRTIMP int __cdecl _dup2(int, int); _CRTIMP int __cdecl _eof(int); _CRTIMP long __cdecl _filelength(int); #ifndef _MAC _CRTIMP long __cdecl _findfirst(const char *, struct _finddata_t *); _CRTIMP int __cdecl _findnext(long, struct _finddata_t *); _CRTIMP int __cdecl _findclose(long); #endif  /* ndef _MAC */ _CRTIMP int __cdecl _isatty(int); _CRTIMP int __cdecl _locking(int, int, long); _CRTIMP long __cdecl _lseek(int, long, int); _CRTIMP char * __cdecl _mktemp(char *); _CRTIMP int __cdecl _open(const char *, int, ...); #ifndef _MAC _CRTIMP int __cdecl _pipe(int *, unsigned int, int); #endif  /* ndef _MAC */ _CRTIMP int __cdecl _read(int, void *, unsigned int); _CRTIMP int __cdecl remove(const char *); _CRTIMP int __cdecl rename(const char *, const char *); _CRTIMP int __cdecl _setmode(int, int); _CRTIMP int __cdecl _sopen(const char *, int, int, ...); _CRTIMP long __cdecl _tell(int); _CRTIMP int __cdecl _umask(int); _CRTIMP int __cdecl _unlink(const char *); _CRTIMP int __cdecl _write(int, const void *, unsigned int);  #if     _INTEGRAL_MAX_BITS >= 64 _CRTIMP __int64 __cdecl _filelengthi64(int); _CRTIMP long __cdecl _findfirsti64(const char *, struct _finddatai64_t *); _CRTIMP int __cdecl _findnexti64(long, struct _finddatai64_t *); _CRTIMP __int64 __cdecl _lseeki64(int, __int64, int); _CRTIMP __int64 __cdecl _telli64(int); #endif  #ifndef _MAC #ifndef _WIO_DEFINED  /* wide function prototypes, also declared in wchar.h  */  _CRTIMP int __cdecl _waccess(const wchar_t *, int); _CRTIMP int __cdecl _wchmod(const wchar_t *, int); _CRTIMP int __cdecl _wcreat(const wchar_t *, int); _CRTIMP long __cdecl _wfindfirst(const wchar_t *, struct _wfinddata_t *); _CRTIMP int __cdecl _wfindnext(long, struct _wfinddata_t *); _CRTIMP int __cdecl _wunlink(const wchar_t *); _CRTIMP int __cdecl _wrename(const wchar_t *, const wchar_t *); _CRTIMP int __cdecl _wopen(const wchar_t *, int, ...); _CRTIMP int __cdecl _wsopen(const wchar_t *, int, int, ...); _CRTIMP wchar_t * __cdecl _wmktemp(wchar_t *);  #if     _INTEGRAL_MAX_BITS >= 64 _CRTIMP long __cdecl _wfindfirsti64(const wchar_t *, struct _wfinddatai64_t *); _CRTIMP int __cdecl _wfindnexti64(long, struct _wfinddatai64_t *); #endif  #define _WIO_DEFINED #endif #endif  /* ndef _MAC */   _CRTIMP long __cdecl _get_osfhandle(int); _CRTIMP int __cdecl _open_osfhandle(long, int);  #if     !__STDC__  /* Non-ANSI names for compatibility */  _CRTIMP int __cdecl access(const char *, int); _CRTIMP int __cdecl chmod(const char *, int); _CRTIMP int __cdecl chsize(int, long); _CRTIMP int __cdecl close(int); _CRTIMP int __cdecl creat(const char *, int); _CRTIMP int __cdecl dup(int); _CRTIMP int __cdecl dup2(int, int); _CRTIMP int __cdecl eof(int); _CRTIMP long __cdecl filelength(int); _CRTIMP int __cdecl isatty(int); _CRTIMP int __cdecl locking(int, int, long); _CRTIMP long __cdecl lseek(int, long, int); _CRTIMP char * __cdecl mktemp(char *); _CRTIMP int __cdecl open(const char *, int, ...); _CRTIMP int __cdecl read(int, void *, unsigned int); _CRTIMP int __cdecl setmode(int, int); _CRTIMP int __cdecl sopen(const char *, int, int, ...); _CRTIMP long __cdecl tell(int); _CRTIMP int __cdecl umask(int); _CRTIMP int __cdecl unlink(const char *); _CRTIMP int __cdecl write(int, const void *, unsigned int);  #endif  /* __STDC__ */  #ifdef  __cplusplus } #endif  #endif  /* _POSIX_ */  #ifdef  _MSC_VER #pragma pack(pop) #endif  /* _MSC_VER */  #endif  /* _INC_IO */

引用 3 楼 Intel0011 的回复:接楼上 https://msdn.microsoft.com/en-us/library/aa246710(v=vs.60).aspx #include <stdio.h> //#include <stdlib.h> //#include <string.h> #include <io.h> #include <fcntl.h> //#include <sys/types.h> #include <sys/stat.h>   int main(void) {    long len;    int fh, result;    FILE *fp1 = fopen("3.txt", "w");    fputs("1234567654321", fp1);    fseek(fp1, -5, SEEK_CUR);    fputs("88", fp1);    len = ftell(fp1);    fclose(fp1);     /* Open a file */    if ((fh = _open("3.txt", _O_RDWR | _O_CREAT, _S_IREAD | _S_IWRITE)) != -1)    {       printf("File length before: %ld\n", _filelength(fh));       if ((result = _chsize(fh, len)) == 0)          printf("Size successfully changed\n");       else          printf("Problem in changing the size\n");       printf("File length after:  %ld\n", _filelength(fh));       _close(fh);    }        return 0; }  没有io.h呢？

引用 3 楼 Intel0011 的回复:接楼上 https://msdn.microsoft.com/en-us/library/aa246710(v=vs.60).aspx #include <stdio.h> //#include <stdlib.h> //#include <string.h> #include <io.h> #include <fcntl.h> //#include <sys/types.h> #include <sys/stat.h>   int main(void) {    long len;    int fh, result;    FILE *fp1 = fopen("3.txt", "w");    fputs("1234567654321", fp1);    fseek(fp1, -5, SEEK_CUR);    fputs("88", fp1);    len = ftell(fp1);    fclose(fp1);     /* Open a file */    if ((fh = _open("3.txt", _O_RDWR | _O_CREAT, _S_IREAD | _S_IWRITE)) != -1)    {       printf("File length before: %ld\n", _filelength(fh));       if ((result = _chsize(fh, len)) == 0)          printf("Size successfully changed\n");       else          printf("Problem in changing the size\n");       printf("File length after:  %ld\n", _filelength(fh));       _close(fh);    }        return 0; }   请问_open是什么函数？使用的是标准库？谢谢

引用 3 楼 Intel0011 的回复:接楼上 https://msdn.microsoft.com/en-us/library/aa246710(v=vs.60).aspx #include <stdio.h> //#include <stdlib.h> //#include <string.h> #include <io.h> #include <fcntl.h> //#include <sys/types.h> #include <sys/stat.h>   int main(void) {    long len;    int fh, result;    FILE *fp1 = fopen("3.txt", "w");    fputs("1234567654321", fp1);    fseek(fp1, -5, SEEK_CUR);    fputs("88", fp1);    len = ftell(fp1);    fclose(fp1);     /* Open a file */    if ((fh = _open("3.txt", _O_RDWR | _O_CREAT, _S_IREAD | _S_IWRITE)) != -1)    {       printf("File length before: %ld\n", _filelength(fh));       if ((result = _chsize(fh, len)) == 0)          printf("Size successfully changed\n");       else          printf("Problem in changing the size\n");       printf("File length after:  %ld\n", _filelength(fh));       _close(fh);    }        return 0; }   好的，谢谢，我试试看，这个与编译器什么的绑定么？我想要一个通用的，不要受什么版本限制什么的

fseek只能控制文件描述的位置，它不会对文件内容做任何修改； 对于楼主的需求，可以通过两种方法实现： 一种覆盖法，文件已经存在的数据，是fseek定位到文件的位置，然后输入"88"，然后后面的数据用空格覆盖； 另一种办法，就是将文件的内容读到内存，在内存里直接操作，然后重新刷到文件里。 至于使用那种办法，要根据实际需求；

引用 4 楼 codedoctor 的回复:我的意思就是直接全部重写。先直接seek到结尾，再全部装入string中进行处理，处理完之后再重新写入 当文件过大时，你这招就不太好用了


Question: C语言VC++6.0最大字段和问题运行出现停止工作，求大神！！！！！！

for(i=1;i<=n;i++)     {         scanf("%d", &a[i]);    /*注意加&*/     } scanf第二个参数应该是地址。


Question: C语言求教

仅供参考  int compress(char array[], int count[]) { //start  	// 0 for char '0' 	// 1 for char '1' 	int flag = 0;   	int len = strlen(array); 	int i = 0;  	int tail = 0; 	count[tail] = 0;  	for (i = 0; i < len; ++i)  	{ 		switch (array[i]) 		{ 		case '0': 			if (flag != 0)  			{ 				flag = 0; 				++tail; 				count[tail] = 0; 			} 			break;  		case '1': 			if (flag != 1) 			{ 				flag = 1; 				++tail; 				count[tail] = 0; 			} 			break;  		default: 			continue; 		}  		++count[tail]; 	}  	return tail; //end }

#include "stdio.h" #define Len 100 	int compress(char array[],int count[ ]) { 	int num; 	int i = 0; 	int j=0;  	while(i<100) 	{ 		num = 0; 		if(array[i]=='0'||array[i]=='1') 		{ 			while(array[i]=='0') { num++;i++;} 			count[j++]=num; 			num = 0;  			while(array[i]=='1'){ num++;i++;} 			count[j++]=num; 		} 		else return j-1; 	} 	return j-1; 	}  int main() { 	char array[Len]={'0','0','0','0','0','1','1','1','1','0','0','0','0','1','1','0','0','1','1','1'}; 	char array1[Len]={'0','0','0','0','0','0','1','1','1','1','0','0','0','1','1','1','1','0','0','0','0','0','1','1'}; 	int count[Len]; 	int i; 	int tail;  	tail = compress(array1,count); 	for(i=0;i<=tail;i++) 		i<tail?printf("%d ",count[i]):printf("%d ",count[i]); }

可以参考这篇：http://blog.csdn.net/u012455213/article/details/45502573

这个就是游程编码啊，顺序扫描连续0的个数和1的个数，转换成数字

压缩算法你不说出来。。。。这个怎么写，，，


Question: C语言问题：判断该天是本年的第几天

#include<stdio.h>  int main() {     int a[12]={31,28,31,30,31,30,31,31,30,31,30,31};     int year,month,day;     int days=0,i;     scanf("%d%d%d",&year,&month,&day);     for(i = 0; i < month -1;i++)         days+=a[i];     days+=day;     if(((year%4==0&&year%100!=0)||(year%400==0))&& month >= 3)         days+=1;     printf("%d\n",days);     return 0; } 参考一下吧 主要是3个问题： 问题1：    for(i = 0; i < month -1;i++)         days+=a[i]; a下标是从0开始，不能从-1开始，若i= 0；那么i-1岂不是-1;所以，i的退出条件应该改为i < month -1 问题2：判断条件，应该是这样的：  if(((year%4==0&&year%100!=0)||(year%400==0))&& month >= 3) 问题3：最后的输出没必要days - year吧。这样得到的是61 - 2017，是一个负值

scanf("%d,%d,%d",&year,&month,&day); scanf("%d %d %d",&year,&month,&day);


Question: 数据结构静态链表（A-B）∪(B-A)伪码不太理解

伪代码不容易看懂，建议从网上找到对应的代码，然后直接看实现代码；

不要迷信书、考题、老师、回帖； 要迷信CPU、编译器、调试器、运行结果。 并请结合“盲人摸太阳”和“驾船出海时一定只带一个指南针。”加以理解。 任何理论、权威、传说、真理、标准、解释、想象、知识……都比不上摆在眼前的事实！  代码功能归根结底不是别人帮自己看或讲解或注释出来的；而是被自己静下心来花足够长的时间和精力亲自动手单步或设断点或对执行到某步获得的中间结果显示或写到日志文件中一步一步分析出来的。 提醒：再牛×的老师也无法代替学生自己领悟和上厕所！ 单步调试和设断点调试（VS IDE中编译连接通过以后，按F10或F11键单步执行，按Shift+F11退出当前函数；在某行按F9设断点后按F5执行停在该断点处。）是程序员必须掌握的技能之一。  《数据结构（C语言描述）》

亲，有人吗。。。


Question: 怎样查看硬盘或U盘地址空间存储的数据?

机械硬盘，从0柱面、0扇区、0磁头开始……

windows用ue、ue studio，linux下用xxd，hexdump

有各种工具软件显示16进制数据的文件。具体可以去网上搜。 自己实现简单的也不是很难。 我写过一个小函数，以16进制显示一段内存数据的//以16进制打印一段内存（字符串） void dumpdata(const char* buff, int len) { 	for (int i = 0; i < len; i++) 	{ 		printf("%02X ", (unsigned char)buff[i]); 	} 	printf("\n"); }

Linux下，可以使用“od -x 文件名”命令查看文件的二进制内容； od -xc file >file.txt是将file的二进制形式的内容放到file.txt文件里，打开file.txt文件就可以看到file文件的二进制内容；  Windows下考虑一下这样的工具： http://blog.csdn.net/andrew57/article/details/51537798

推荐使用WinHex软件查看硬盘或文件或内存中的原始字节内容。


Question: 一个小问题，关于共同体

静态变量存储的时候，如果没有初值，那么就是 0 . 而你的堆栈变量，如果没有初值，那么就是随机的。 int 是 4 个字节的，而 char[2] 是 2 个字节的。你需要把 4 个字节都赋值。

因为一个int有4字节，而char x[2]只有两字节，你实际只对int的两个字节进行了赋值，另外两个字节没有赋值，是随机值，输出什么取决于编译器实现。如果另外两个字节刚好为0，结果就是266，但你自己不能这样去保证

如果你先用 memset(&a, 0, sizeof(Cookies))进行清零的步骤，那么得到的是你希望的结果。

内存中的随机值，在联合中，int的高32位没赋值，随机了。


Question: 计算机入门，关于指针

谢谢。

http://edu.csdn.net/course/detail/2344 C语言指针与汇编内存地址-一.代码要素

printf里面的%和变量的一一对应关系 scanf里面的%和变量以及变量前加不加&的一一对应关系 是C代码中非常容易出错的地方，而且通常编译还不出错。 所以在编译源代码之前值得专门仔细检查一遍甚至多遍。

%c是输出字符，%d输出是十进制数

因为是用%d输出的，所以输出的就是ASCII值，若是用%c输出则是ASCII字符； #include<stdio.h>  int main() {     char a='w',b='c',*pa,*pb,*pc;     pa = &a;     pb = &b;     printf("a:%c,b:%c,*pa:%c,*pb:%c\n",a,b,*pa,*pb);     pc=pa;     pa=pb;     pb=pc;     printf("a:%c,b:%c,*pa:%c,*pb:%c\n",a,b,*pa,*pb); }     pc=pa;     pa=pb;     pb=pc; 这样的交换只是交换了指针指向的地址，即pa原来指向&a,pb指向&b，通过这三条语句后，就改变了pa, pb的指向，即pa指向&b, pb指向了&a，但是并没有改变变量a和变量b的值。

你用%d輸出，那不就是ASCII碼值！


Question: 有人可以看看吗？

首先说一下你的需求在哪里用，如果是嵌入式设备，带系统的可以考虑用sleep(1)，休眠1秒；如果是不带系统的，比如单片机，那么要根据单片机的CPU频率。一般可以用while循环 比如  while (i < 10000)     ;  上面的代码循环10000次表示一秒；

#include <iostream> #include <Windows.h>  int main() { 	for (int i = 0; i <= 100; i++) 	{ 		std::cout << i << std::endl; 		Sleep(1000); 	} }这个？

啥叫用函数延迟？ Sleep可以么


Question: 有关c语言if语句选择输出结构体中数据

结构体比较不能直接拿数和结构比较，应该是拿数据和结构体的某个成员比较；

if后面必须带着一个语句或语句块，你这段显然有语法错误：   for ( i = 0; i < 4; i++)  {  if(j>tra[i].price)  }

scanf("%d", j);  改成：scanf("%d", &j);i  f(j>tra[i].price) 后面加上你要的执行的语句

scanf("%d", j); -> scanf("%d", &j);


Question: C语言初学者，求各位帮忙看看这道ACM我为什么错了

#include <stdio.h> #include <stdlib.h>  int main() {     int i, j, k;     int tm, num, ch, cnt;     char *list;      scanf("%d", &tm);      k = 0;     while (k < tm) {         scanf("%d", &num);         getchar();   /*for '\n' */          list = (char *)malloc(sizeof(char) * num);         if (!list)             return -1;          i = 0;         cnt = 0;         while ((ch = getchar()) != '\n') {             if (ch == ' ')                 continue;             list[i] = ch;             for (j = 0; j < i; j++)                 if (ch == list[j])                     break;             if (j >= i)                 cnt++;             i++;             if (i >= num)                 break;         }         printf("case#%x: %d\n", k+1, cnt);         k++;      }      /*     int t,l,m,c[1000],k,y;     char j1;     char a[1000][1000],b[1000][1000];     scanf("%d",&t);     for(int i=0;i<t;i++)     {         k=0;m=0;y=1;         scanf("%d",&c[i]);         getchar();     /*for '\n' */         while((j1=getchar())!='\n')         {             if(j1!=' ')             {                 b[i][k]=j1;                 k++;             }         }         for(int j=0;j<k;j++)         {             l=0;             for(int z=j;z<k;z++)             {                 if(b[i][j]==b[i][z])                 {                     l+=1;                 }             }             if(l==1)             {                 m++;             }         }         printf("Case #%d:%d\n",i+1,m);     }     */     return 0; }  参考一下吧；   scanf("%d",&c[i]);去掉第一个参数的'\n'，然后在scanf后面加一句getchar();，该getchar()作为接收scanf输入后的换行符'\n'


Question: 有关UNIX系统识别文件结束

我也看到这里！

引用 2 楼 adlay 的回复:都是说的没有使用特殊字符来作为文件结束的标记 谢谢！

引用 1 楼 user-3 的回复:这两种说法并不矛盾，后者更针对于文本文件 呃呃，我似乎有点明白您的意思了。 感谢版主，百忙之中抽时间回答我的问题。十分感谢！

都是说的没有使用特殊字符来作为文件结束的标记

这两种说法并不矛盾，后者更针对于文本文件


Question: 求助！读取文件中数据然后输出时每次循环都会多一个0，代码如下，怎么办？

在你的程序加一个判断也可以 #include <stdio.h> #include <stdlib.h> #include <string.h>  int main(void) {    char str[90] = { '\0' };    double a[11];    char *b = NULL;    int i;    FILE *fp1 = fopen("3.txt", "r");    if (fp1)    {         do       {          if (!fgets(str, 89, fp1)) break; //           b = strtok(str, " ");          for (i = 0; i < 11; ++i)          {              if (b)             {                a[i] = atof(b);                b = strtok(NULL, " ");                printf("%f ", a[i]);              }          }                                                                                printf("\n");       } while (!feof(fp1));       fclose(fp1);    }    else    {       printf("无文件\n");       return -1;    }    return 0; }

如果文件是固定格式的，可以使用 fscanf() 函数读数据 例如文件内容为 str 1.0 20.0 10.12 可以这样写 fscanf(fp, "%s %f %f %f", ...);

直接用fgets判断文件尾 #include <stdio.h> #include <stdlib.h> #include <string.h>  int main(void) {    char str[90] = { '\0' };    double a[11];    char *b = NULL;    int i;     FILE *fp1 = fopen("3.txt", "r");    if (fp1)    {         while (fgets(str, 89, fp1))       {            b = strtok(str, " ");          for (i = 0; i < 11; ++i)          {              if (b)             {                a[i] = atof(b);                b = strtok(NULL, " ");                printf("%f ", a[i]);              }          }                                                                                printf("\n");       }       fclose(fp1);    }    else    {       printf("无文件\n");       return -1;    }    return 0; }

或者用 fgetc 预读一个字符再判断文件尾 #include <stdio.h> #include <stdlib.h> #include <string.h>  int main(void) {    char str[90] = { '\0' };    double a[11];    char *b = NULL;    int i;    int c;     FILE *fp1 = fopen("3.txt", "r");    if (fp1)    {         do       {          c = fgetc(fp1);          if (c == EOF) return -2;          else ungetc(c, fp1);                fgets(str, 89, fp1);                    b = strtok(str, " ");          for (i = 0; i < 11; ++i)          {              if (b)             {                a[i] = atof(b);                b = strtok(NULL, " ");                printf("%f ", a[i]);              }          }                                                                                printf("\n");       } while (!feof(fp1));       fclose(fp1);    }    else    {       printf("无文件\n");       return -1;    }    return 0; }

#include <stdio.h> #include <stdlib.h> #include <string.h>  int main(void) {    char str[90] = { '\0' };    double a[11];    char *b = NULL;    int i;    FILE *fp1 = fopen("3.txt", "r");    if (fp1)    {         //文件最后没有单独的换行        #if 01       do       {          fgets(str, 89, fp1);                    b = strtok(str, " ");          for (i = 0; i < 11; ++i)          {              if (b)             {                a[i] = atof(b);                b = strtok(NULL, " ");                printf("%f ", a[i]);              }          }                                                                                printf("\n");       } while (!feof(fp1));       fclose(fp1);       #endif       //文件最后有单独的换行       #if 0       fgets(str, 89, fp1);       while (!feof(fp1))        {          b = strtok(str, " ");          for (i = 0; i < 11; ++i)          {              if (b)             {                a[i] = atof(b);                b = strtok(NULL, " ");                printf("%f ", a[i]);              }          }                                                                                printf("\n");          fgets(str, 89, fp1);       }       #endif     }    else    {       printf("无文件\n");       return -1;    }    return 0; }

main函数没有定义位double类型的。  建议把你的文件内容贴出来，另外，顺便把str打出来，看看strtok之前str是什么字符串； 另外注意fgets会将'\n'换行符读到str里。

是不是每一行最后一列数据后面由空格啊，你可以用while判断strtok结束，并结合判断a[i]的值是否为0.0来控制输出。


Question: C语言新手求助

#include <stdio.h>  int Digit2Char (long int x,char a[]) {   long int x1=x; //复制一个同样的值   int j,times,flag,t,b[20],k,sum=0;   /*for(j=7;(j>=0)&&(x1!=0);j--) //从个位开始赋值给b数组   //error  串长小于8   { 	b[j]=x1%10; 	x1=x1/10; 	sum+=b[j];   }   */   for(j = 0; x1 ; ++j)   { 	  b[j] = x1 % 10; 	  x1 /= 10; 	  sum += b[j];   }       for(times=1;times<j;times++)//比较次数为7次            //修改     for(flag=0;flag<j-times;flag++)//比较相邻两个数的位置     if(b[flag+1]>b[flag])     t=b[flag+1],b[flag+1]=b[flag],b[flag]=t;//比较前后数字大小并排序     for(k=0;k<j;k++)     //修改 	a[k]=b[k] +'0'; //把b数组的数字转换为a数组的字符      a[j] = '\0';   if (x<=99999999&&x>=0)//判断是否为8位以内的有效数字 	return sum;   else     return 0;//有效数字超过8位返回0 }   int main(void) { 	char a[7] = "\0";  	long int y; 	scanf("%ld",&y);  	if(Digit2Char(y,a)) 		printf("%d,%s",Digit2Char(y,a),a); 	else printf("%s\n","Input Error!\n"); 	 	return 0; }

我也是新人，不一定是最简单的方法

#include<stdio.h> #include<math.h> void main() { 	int n,a[8],sum,i,j,k,t,new,g; 	scanf("%d",&n); 	for(i=0,sum=0;n;i++) 	{ 		a[i]=n%10; 		sum+=a[i]; 		n/=10; 	} 	g=i;/*记住输入的是几位数*/ 	if(g<=8) 	{ 	   for(i=0;i<g-1;i++) 	   { 		   for(j=i+1,k=i;j<g;j++) 		   if(a[k]>a[j])k=j; 		   if(k!=i){t=a[i];a[i]=a[k];a[k]=t;} 	   } 	   for(i=0,new=0;i<g;i++) 	   new+=a[i]*pow(10,i); 	   printf("%d,%d\n",sum,new); 	} 	else printf("Input Error!\n"); }


Question: 一个C语言，很困扰，请大神解答！！！

s[j+1]=s[j]; s[j+1]='*';

while(s[i+1+n]!='\0') n++; 这两行代码就是计算当前i位置距离字符串末尾还有多少个字符，可以通过在while循环后打出n的值来确认； 最后的执行结果是在每个数字后面都加一个*号，代码也是这样执行的。 那么楼主想实现什么？

引用 楼主 qq_36974603 的回复:这部分我有疑问：当循环到第一个数字字符3时，i=2，然后判断s[i+1+n]!='\0'之后，不是应该执行n++;语句然后n=1吗？ 如果按照我的思路，应该接下来是j=4,然后s[5]=s[4];s[4]='*';才对啊！可答案好像不是我这样的！ 第1句是对的，但接下来不是立即执行第2句，因为循环还未结束，等循环结束后，n的值是8，所以j的值不是4，而是2+8+1=11 加个输出语句看看便知 void fun(char *s) {    int i,j,n;    for(i=0;s[i]!='\0';i++)       if(s[i]>='0' && s[i]<='9')       {          n=0;                    while(s[i+1+n]!='\0') n++;          //printf("%d\n", n); return;           for(j=i+n+1;j>i;j--)          {             //printf("%d\n", j); return;             s[j+1]=s[j];          }          s[j+1]='*';          i=i+1;       } }


Question: 求助一道简单的acm试题

引用 27 楼 weixin_41259211 的回复:[quote=引用 26 楼 FancyMouse的回复:]你们哪里来的信心32位int能存的下答案。输入如果是3w个Q，3w个A，再3w个Q呢 改成long以后也不行，答案是错误的[/quote] 不好意思，只考虑逻辑，类型用错了，把int改成long吧(不确定你用的什么编译器，建议还是改成long long吧)，把最后输出也一并改了：printf("%ld\n", ...)或printf("%lld\n"...)。改完再试试呢。(nums类型最好也改了，5w*4w会超int)

引用 26 楼 FancyMouse的回复:你们哪里来的信心32位int能存的下答案。输入如果是3w个Q，3w个A，再3w个Q呢 改成long以后也不行，答案是错误的

引用 24 楼 weixin_41259211的回复:[quote=引用 22 楼 _暮雨潇湘_的回复:] #include <stdio.h> #include <string.h>  #define MAXN (100000+2)  char input[MAXN]; int  nums[MAXN];  // 注意左结合 // 先计算能结合出多少个'AQ' // 再计算能结合出多少个'QAQ'  // 求每个'A'后面跟了多少个'Q' void calc_q_nums_after_a(char* s, int n, int* nums) { 	int i, num = 0; 	for (i = n-1; i >= 0; i--) { 		if (s[i] == 'Q') { 			num++; 		} else if (s[i] == 'A') { 			nums[i] = num; // 第一步收割, 'Q'左结合'A'得到'AQ'数量 		} 	} }  // 求'QAQ'出现次数 int calc_qaq_nums(char* s, int n, int* nums) { 	int i, aq = 0, qaq = 0; 	for (i = n-1; i >= 0; i--) { 		if (s[i] == 'A') { 			aq += nums[i]; // 到现在为止出现'AQ'的数量 		} else if (s[i] == 'Q') { 			qaq += aq; // 第二步收割, 'AQ'左结合'Q'得到'QAQ'的数量 		} 	} 	return qaq; }  int main(void) { 	scanf("%s", input); 	int n = strlen(input); // O(n) 	calc_q_nums_after_a(input, n, nums); // O(n) 	printf("%d\n", calc_qaq_nums(input, n, nums)); // O(n) 	return 0; }   试试这样呢？ 为什么会有编译错误的提示，我感觉是对的！[/quote] 不对，我修改了下，可以运行了 但是答案错误

引用 22 楼 _暮雨潇湘_的回复: #include <stdio.h> #include <string.h>  #define MAXN (100000+2)  char input[MAXN]; int  nums[MAXN];  // 注意左结合 // 先计算能结合出多少个'AQ' // 再计算能结合出多少个'QAQ'  // 求每个'A'后面跟了多少个'Q' void calc_q_nums_after_a(char* s, int n, int* nums) { 	int i, num = 0; 	for (i = n-1; i >= 0; i--) { 		if (s[i] == 'Q') { 			num++; 		} else if (s[i] == 'A') { 			nums[i] = num; // 第一步收割, 'Q'左结合'A'得到'AQ'数量 		} 	} }  // 求'QAQ'出现次数 int calc_qaq_nums(char* s, int n, int* nums) { 	int i, aq = 0, qaq = 0; 	for (i = n-1; i >= 0; i--) { 		if (s[i] == 'A') { 			aq += nums[i]; // 到现在为止出现'AQ'的数量 		} else if (s[i] == 'Q') { 			qaq += aq; // 第二步收割, 'AQ'左结合'Q'得到'QAQ'的数量 		} 	} 	return qaq; }  int main(void) { 	scanf("%s", input); 	int n = strlen(input); // O(n) 	calc_q_nums_after_a(input, n, nums); // O(n) 	printf("%d\n", calc_qaq_nums(input, n, nums)); // O(n) 	return 0; }   试试这样呢？ 为什么会有编译错误的提示，我感觉是对的！

这个好像可以...

引用 7 楼 weixin_41259211的回复:[quote=引用 6 楼 MyCout的回复:]   我觉得num统计数量时应该放在    if(p[i]=='Q'||p[i]=='A')         {             a[n]=p[i];             n++;         } 里面，当前num的统计值是超过Q,A数量的，后面的内存是未知的，可能会出现问题，我用你的程序测试了下，一般情况值是正确的。 放到里面以后你测试了吗？[/quote] 放到里面就是时间超限，我觉得算法有问题

引用 6 楼 MyCout的回复:我觉得num统计数量时应该放在    if(p[i]=='Q'||p[i]=='A')         {             a[n]=p[i];             n++;         } 里面，当前num的统计值是超过Q,A数量的，后面的内存是未知的，可能会出现问题，我用你的程序测试了下，一般情况值是正确的。 放到里面以后你测试了吗？

引用 1 楼 学习编程的萌新的回复:同学你看看我这个  我也是初学者 #include<iostream> #include<cstring> using namespace std; char s[100005];  int main(){ 	int i,j,len,k,cnt=0;  	cin>>s; 	len = strlen(s); 	for(i=0;i<len;i++){ 		if(s[i]=='Q') 		for(j=i+1;j<len;j++){ 			if(s[j]=='A') 			for(k=j+1;k<len;k++){ 				if(s[k]=='Q') 				cnt++; 			} 		} 	} 	cout<<cnt<<endl; 	return 0; } 额  看了   时间超限的错误

引用 1 楼 学习编程的萌新的回复:同学你看看我这个  我也是初学者 #include<iostream> #include<cstring> using namespace std; char s[100005];  int main(){ 	int i,j,len,k,cnt=0;  	cin>>s; 	len = strlen(s); 	for(i=0;i<len;i++){ 		if(s[i]=='Q') 		for(j=i+1;j<len;j++){ 			if(s[j]=='A') 			for(k=j+1;k<len;k++){ 				if(s[k]=='Q') 				cnt++; 			} 		} 	} 	cout<<cnt<<endl; 	return 0; } 代码不全啊，再发一遍看看￣ ￣

引用 2 楼 MyCout的回复:值不对还是？ 值不对，我已经发现了算法有问题，但不知道怎么修改了

刚那个复杂度1e15，估计也会超时 比如QAQJLZBBQ，实际对你有用的只有QAQQ，所以处理后变为1001. 实际你可以把一个完整的串分为三个部分，第一部分的1的数目*第二部分的0的数目*第三部分的1的数目，当你把所有的分法遍历之后就是总的个数了。 假设处理之后是第三部分是01011，第一部分确定的情况下，那么numAQ（第二部分的0的数目*第三部分的1的数目）的所有分法总和是1*3+1*2+2*2+2*1，当左边是新加一个0时，numAQ先加个3，再所有左加数加一，实际加了了3+3+2+2+1，这个数字就是二三部分右起第0到第5，4，3，2，1个部分1的总数，算的话应该是右起第0到第4，3，2，1个部分1的总数+右起第0到第4的1的总数加0（因为新加的不是1），同理如果左边再加个0，只需要NumAQ+Num1，1也是一样的，这样时间复杂度就是1e5了，过程能懂的话算法多写几次就行了

引用 19 楼 user-5的回复:新建一个bool[]，Q为true，A为False，其余全部丢掉；              for(int i = 0; i < n; i++)             {                 if (a[i])                 {                     for(int j = i + 1; j < n; j++)                     {                         if (!a[j])                         {                             for (int k = j + 1; k < n; k++)                             {                                 if (a[k])                                 {                                     num++;                                 }                             }                         }                     }                 }             } 额，不太明白，新手，能把代码给我看看学习下吗

我感觉这问题我就不太了解了 有测试用例还可以了解哈

引用 16 楼 MyCout的回复:/*#include <stdlib.h> 开始这句 你把/*去掉再使用的吧  不然编译都不会过 嗯....这点我还是知道的，去掉了

引用 14 楼 MyCout的回复:你可以把平台测试错误相关的信息发出来比较好 不然信息太少了 我的是时间超限（但我知道算法有问题了），楼上那个算法是答案错误，网站只给了这两个信息


Question: 循环语句知识 求大佬解决

不执行continue那么，就会执行后面的printf。continue是停止之后后面的语句，从当前位置跳转到循环体开始位置：修改循环变量，判断循环条件，执行循环体；

if语句只对它下面的第一条语句有效。 不管if条件成不成立，都会执行printf语句。

路上两位说的都对。 如果if条件不满足，则不会执行continue语句（if的作用域就continue这一句），后面的printf语句是会执行的。 如果if条件满足，则会执行continue语句，continue执行会跳过本次for循环后面的语句，直接进入下一次for循环。  楼主可以单步调试感受一下，下面三种方式的区别：  #include<stdio.h> int main() { 	int n; 	for(n=100;n<=200;n++) 	{ 		if(n%3==0) 			continue;			 		printf("%d",n); 	} 	printf("\n"); 	return 0; }   #include<stdio.h> int main() { 	int n; 	for(n=100;n<=200;n++) 	{ 		if(n%3==0) 			//continue;			 		printf("%d",n); 	} 	printf("\n"); 	return 0; }   #include<stdio.h> int main() { 	int n; 	for(n=100;n<=200;n++) 	{ 		//if(n%3==0) 			continue;			 		printf("%d",n); 	} 	printf("\n"); 	return 0; }  另建议楼主写代码if条件时，加上{}养成好的习惯：  #include<stdio.h> int main() { 	int n; 	for(n=100;n<=200;n++) 	{ 		if(n%3==0) 		{ 			continue; 		} 		printf("%d",n); 	} 	printf("\n"); 	return 0; }

虽然不执行continue（不重新开始下一次循环），但还是会继续执行完本次循环，也就是后面的代码仍然会继续执行

if(n%s==0) -->  if(n%3==0)  continue; 意思是能被3整除，执行 continue，即跳过下面的printf，执行下一个循环 不能被3整除时不执行 continue，再执行下面的printf


Question: 新手求助，为什么会产生default segment?

Linux： 进程意外退出会在当前目录下产生‘core’文件或形如‘core.数字’的文件比如‘core.1234’ 使用命令 gdb 运行程序名 core或core.数字 进入gdb然后使用bt命令 可以查看进程意外退出前函数调用的堆栈，内容为从上到下列出对应从里层到外层的函数调用历史。 如果进程意外退出不产生core文件，参考“ulimit -c core文件最大块大小”命令

崩溃的时候在弹出的对话框按相应按钮进入调试，按Alt+7键查看Call Stack即“调用堆栈”里面从上到下列出的对应从里层到外层的函数调用历史。双击某一行可将光标定位到此次调用的源代码或汇编指令处，看不懂时双击下一行，直到能看懂为止。

struct student * s[5]; //只声明了结构指针数组，没有未该指针初始化 s[0]指向哪里，没有为指针分配结构，需要分配一个结构，再将结构的地址赋给s[0] 其他同理


Question: 程序中所说的线程、进程， 和CPU的线程（如四核八线程）有什么区别

程序的线程是指能同时并发执行的逻辑单元的个数，是通过时间片分配算法实现的；cpu的线程是指将cpu的指令执行过程（取指、译指、执行，访存、写数）做出流水线从而提高并发度的方法

引用 5 楼 zhao4zhong1 的回复:CPU的线程是指指令流水线的条数。我猜。 呃呃，赵老师您好！

CPU的线程是指指令流水线的条数。我猜。

CPU的指的是CPU可以同时运行的线程数量，是可以同时执行的代码路径数量，程序中的表示你实际用到的，如果程序的线程数多于CPU的线程数，那敢并不是真正的并行，各线程会占用在一个很短的时间片里依次得到执行，用户看似是同时运行的

程序说的线程进程是软件的概念。一个程序就是一个进程，每个进程至少1个线程（在windows系统是这样）。 操作系统通过时间分片算法，可以在一个CPU上让多个线程轮流执行，看起来似乎是很多线程进程同时运行了。 CPU的线程是硬件的概念。八线程就是能让八个线程同步执行。

进程是线程的容器，系统的调度单位是线程，程序的线程需要在CPU核上的线程上跑


Question: C语言指针问题

http://edu.csdn.net/course/detail/2516 C语言指针与汇编内存地址-三.数组和二维数组

。。。弄错了(*(p + 1)[2])才是p[1][2]   这里的就是p[3][0]

仅供参考：//char (*(*x[3])())[5];//x是什么类型的变量? // //分析C语言声明，关键是搞清楚这个变量是个什么东西（函数、指针、数组）， //是函数那么剩下的就是他的参数和返回值， //是指针那剩下部分是说明他指向什么， //是数组剩下的部分就是说明数组的成员是什么类型。 //解析C语言声明规则： //从左侧第一个标识符开始，按照优先级进行结合。*表示是..的指针，const表示只读的，volatile表示可变的，[]表示是数组，()表示是函数。 // //x和[3]结合说明是一个大小为3的数组，该数组的每个元素为一类指针，该类指针指向一类函数，该类函数无参数，返回一类指针，该类指针指向一个大小为5的char型数组 #include <stdio.h> #include <typeinfo.h> char num[5]; char (*x00())[5] {     return # } int main() {     char (*(*x[3])())[5];//是个数组，大小为3     char (*(*x0  )())[5];//数组的元素，是个函数指针     char (*( x00 )())[5];//函数原型，参数为空，返回值为指针     char (*  x000   )[5];//返回值      x0 = x00;     x[0] = x0;     x[1] = x0;     x[2] = x0;     printf("typeid(x).name() is %s\n",typeid(x).name());     return 0; } //typeid(x).name() is char (* (__cdecl**)(void))[5]

这里考察数组的地址都是连续，所以可以这样赋值，(*ptr)[2]是一个数组指针， *((ptr + 1)[2])表示ptr[1][2]即ptr[2][0], 降维的话是Ptr[4]， a[4][3]二维将一维可以变为A[12],   Ptr[4]]就是A[4]    所以值是5

ptr指向的数组是a[4][2];因此列数长度是2;*((ptr+1)[2])即ptr[3][0]

http://edu.csdn.net/course/detail/2344 C语言指针与汇编内存地址-一.代码要素

你懂汇编么？反汇编看下数组在汇编里怎么表示就懂了，很简单的事情

ptr是一个指向一维数组的指针，该一维数组有两个元素 所以ptr+1指向下一个一维数组的指针，跳过的距离与一维数组有几个元素有关

(ptr + 1)[2]相当于*(ptr + 1 +2) -> *(ptr + 3)  *((ptr + 1)[2]) ->  **(ptr + 3) ptr+0 -> 1 2 ptr+1 -> 3 4  ptr+2 -> 5 6 ptr+3 -> 7 8 so,  **(ptr + 3) == 7  *(*(ptr + 3)+1) == 8

刚才调试了下看了地址得到的表面理解，但是不知道对不对，请大神们指正： 1.如何取值取决于指针，*(ptr+1)要以2列为标准，而比如*(a+1)就要以3列为标准计算 2.(ptr+1)[2]中的[2]部分仍是行控制，表示在ptr向下+1行后再向下+2行 3.(ptr+1)[2]+1中的+1部分才是列控制，表示在此行向右移动一列


Question: 新手刚学C语言，想修改一段代码可以帮下忙吗

可以是可以，但显示中文会影响位置 另putchar(f<=0.0f?".:-=*#%@"[(int)(f*-8.0f)]:3);是不是改为 putchar(f<=0.0f?".:-=*#%@"[(int)(f*-8.0f)]:‘3’); #include <stdio.h> #include <math.h> #include <locale.h>  int main(void) {    float x, y, z, f;    setlocale(LC_ALL, "chs");     for (y = 1.5f; y > -1.5f; y -= 0.1f)    {       for (x = -1.5f; x < 1.5f; x += 0.05f)       {          z = x * x + y * y - 1;          f = z * z * z - x * x * y * y * y;          //putwchar(f <= 0.0f ? L".:-=*#%@"[(int)(f * -8.0f)] : L'8'); //有些平台上不显示          f <= 0.0f ? wprintf(L"%c", L".:-=*#%中"[(int)(f * -8.0f)]) : wprintf(L"%c", L'8');       }       putchar('\n');    }     //getchar();    return 0; }

putchar只能输出单个字符，而你试图输出一大串字符串，请改用printf

要输出非Ascii字符，需要用到另外一些函数。  #include <stdio.h> #include <stdlib.h> #include <locale.h> #include <wchar.h>  void main()     {     setlocale(LC_ALL, "");      wprintf(L"Why? 为什么？\n");     }  给一个简单范例，这块深入学习需要了解Unicode,Encoding等概念，还是比较麻烦的。

换成中文可以，但是一个中文字符不能用一个字符表示；建议看一下查一下putwchar； 不过直接用putwchar也是不行的，还得熟悉这个算法；


Question: 求助！Debug/shiyan.exe : fatal error LNK1169: one or more multiply defined symbols

改为以下即可 #include<stdio.h>  int jj(int a[500],int b[500],int n,int m) { 	int i, j, sum=0; 	for(i=0;i<n;i++) 	{ 		for(j=0;j<m;j++) 		{ 			if(a[i]==b[j]) 			{ 				printf("%d ",a[i]); 				sum=1; 			} 		} 	} 	if(sum==0)printf("空"); 	printf("\n"); 	return 0; }  int bj(int a[500],int b[500],int n,int m) {       int i, j;  	for(i=0;i<n;i++) 	{ 		printf("%d ",a[i]); 	} 	for(i=0;i<m;i++) 	{ 		int sum=0; 		for(j=0;j<n;j++) 		{ 			if(b[i]==a[j])sum++; 		} 		if(sum==0)printf("%d ",b[i]); 	} 	printf("\n"); 	return 0; }  int cj(int a[500],int b[500],int n,int m) { 	int i, j, sum=0; 	for(i=0;i<n;i++) 	{ 		int k=0; 		for(j=0;j<m;j++) 		{ 			if(a[i]==b[j])k=1; 		} 		if(k==0) 		{ 			printf("%d ",a[i]); 			sum=1; 		} 	} 	if(sum==0)printf("空"); 	printf("\n"); 	return 0; }  int main() { 	int a[500],b[500]; 	int i,j,k,n,m; 	printf("A集合元素的个数："); 	scanf("%d",&n); 	printf("A集合的元素（两个元素之间用空格隔开）："); 	for(i=0;i<n;i++) 		scanf("%d",&a[i]); 	printf("B集合元素的个数："); 	scanf("%d",&m); 	printf("B集合的元素（两个元素之间用空格隔开）："); 	for(j=0;j<m;j++) 		scanf("%d",&b[j]); 	printf("操作指令：输入1求交集，输入2求并集，输入3求差集，输入0退出程序。\n");  	while(1) 	{ 		scanf("%d",&k); 		if(k==0)break; 		else if(k==1) 		{ 			printf("交集："); 			jj(a,b,n,m); 		} 		else if(k==2) 		{ 			printf("并集："); 			bj(a,b,n,m); 		} 		else if(k==3) 		{ 			printf("差集："); 			cj(a,b,n,m); 		} 		else printf("The input is error! Please enter again.\n"); 	} 	return 0;	 }


Question: c语言问题，大佬们提供下思路

感谢感谢谢谢大佬的帮助，平时c primer plus基本没看，内容大多晦涩难懂

#include <stdio.h>  struct train {     char code[15];     //车次     char data[15];     //日期     char lp[15];       //left place 起点     char ap[15];       //arrive place 终点     char lt[15];       //left time 开车时间     char at[15];       //arrive time 到达时间     int  price;       // 票价 };  void train(void) {     struct train tn[4];     int i;      for (i = 0; i < 4; i++)     {         printf("请输入车次");         scanf("%s", tn[i].code);         printf("请输入日期");         scanf("%s", tn[i].data);         printf("请输入起点");         scanf("%s", tn[i].lp);         printf("请输入终点");         scanf("%s", tn[i].ap);         printf("请输入开车时间");         scanf("%s", tn[i].lt);         printf("请输入到达时间");         scanf("%s", tn[i].at);         printf("请输入票价");         scanf("%d", &tn[i].price);     } } 参考一下吧；  结构体声明，一般会放在函数外，结构体定义变量和数组，建议还是看一下书本，看书本上例子是怎么用的。基础知识，建议多翻翻书，敲敲书本上的例子代码；


Question: C语言如何实现覆盖多行输出?

引用 5 楼 cfjtaishan 的回复:[quote=引用 4 楼 iloveyou418 的回复:] 清屏，你现在看到的很多图像都是通过刷新来进行的，一帧一帧刷新。。。 你这个只需要数据产生变化才进行shuaxin1就可以了~前提是楼主的程序北京得做成图片[/quote] 刷新只是一个说吧~，1秒60帧,我一秒钟做60次输出，每次输出前清屏。。。。为啥非要是图片？

仅供参考：#include <windows.h> #include <stdio.h>  void ConPrint(char *CharBuffer, int len); void ConPrintAt(int x, int y, char *CharBuffer, int len); void gotoXY(int x, int y); void ClearConsole(void); void ClearConsoleToColors(int ForgC, int BackC); void SetColorAndBackground(int ForgC, int BackC); void SetColor(int ForgC); void HideTheCursor(void); void ShowTheCursor(void);  int main(int argc, char* argv[]) {    HideTheCursor();    ClearConsoleToColors(15, 1);    ClearConsole();    gotoXY(1, 1);    SetColor(14);    printf("This is a test...\n");    Sleep(5000);    ShowTheCursor();    SetColorAndBackground(15, 12);    ConPrint("This is also a test...\n", 23);    SetColorAndBackground(1, 7);    ConPrintAt(22, 15, "This is also a test...\n", 23);    gotoXY(0, 24);    SetColorAndBackground(7, 1);    return 0; }  //This will clear the console while setting the forground and //background colors. void ClearConsoleToColors(int ForgC, int BackC) {    WORD wColor = ((BackC & 0x0F) << 4) + (ForgC & 0x0F);    //Get the handle to the current output buffer...    HANDLE hStdOut = GetStdHandle(STD_OUTPUT_HANDLE);    //This is used to reset the carat/cursor to the top left.    COORD coord = {0, 0};    //A return value... indicating how many chars were written    //not used but we need to capture this since it will be    //written anyway (passing NULL causes an access violation).    DWORD count;     //This is a structure containing all of the console info    // it is used here to find the size of the console.    CONSOLE_SCREEN_BUFFER_INFO csbi;    //Here we will set the current color    SetConsoleTextAttribute(hStdOut, wColor);    if(GetConsoleScreenBufferInfo(hStdOut, &csbi))    {       //This fills the buffer with a given character (in this case 32=space).       FillConsoleOutputCharacter(hStdOut, (TCHAR) 32, csbi.dwSize.X * csbi.dwSize.Y, coord, &count);        FillConsoleOutputAttribute(hStdOut, csbi.wAttributes, csbi.dwSize.X * csbi.dwSize.Y, coord, &count);       //This will set our cursor position for the next print statement.       SetConsoleCursorPosition(hStdOut, coord);    } }  //This will clear the console. void ClearConsole() {    //Get the handle to the current output buffer...    HANDLE hStdOut = GetStdHandle(STD_OUTPUT_HANDLE);    //This is used to reset the carat/cursor to the top left.    COORD coord = {0, 0};    //A return value... indicating how many chars were written    //   not used but we need to capture this since it will be    //   written anyway (passing NULL causes an access violation).    DWORD count;    //This is a structure containing all of the console info    // it is used here to find the size of the console.    CONSOLE_SCREEN_BUFFER_INFO csbi;    //Here we will set the current color    if(GetConsoleScreenBufferInfo(hStdOut, &csbi))    {       //This fills the buffer with a given character (in this case 32=space).       FillConsoleOutputCharacter(hStdOut, (TCHAR) 32, csbi.dwSize.X * csbi.dwSize.Y, coord, &count);       FillConsoleOutputAttribute(hStdOut, csbi.wAttributes, csbi.dwSize.X * csbi.dwSize.Y, coord, &count);       //This will set our cursor position for the next print statement.       SetConsoleCursorPosition(hStdOut, coord);    } }  //This will set the position of the cursor void gotoXY(int x, int y) {    //Initialize the coordinates    COORD coord = {x, y};    //Set the position    SetConsoleCursorPosition(GetStdHandle(STD_OUTPUT_HANDLE), coord); }  //This will set the forground color for printing in a console window. void SetColor(int ForgC) {    WORD wColor;    //We will need this handle to get the current background attribute    HANDLE hStdOut = GetStdHandle(STD_OUTPUT_HANDLE);    CONSOLE_SCREEN_BUFFER_INFO csbi;     //We use csbi for the wAttributes word.    if(GetConsoleScreenBufferInfo(hStdOut, &csbi))    {       //Mask out all but the background attribute, and add in the forgournd color       wColor = (csbi.wAttributes & 0xF0) + (ForgC & 0x0F);       SetConsoleTextAttribute(hStdOut, wColor);    } }  //This will set the forground and background color for printing in a console window. void SetColorAndBackground(int ForgC, int BackC) {    WORD wColor = ((BackC & 0x0F) << 4) + (ForgC & 0x0F);;    SetConsoleTextAttribute(GetStdHandle(STD_OUTPUT_HANDLE), wColor); }  //Direct console output void ConPrint(char *CharBuffer, int len) {    DWORD count;    WriteConsole(GetStdHandle(STD_OUTPUT_HANDLE), CharBuffer, len, &count, NULL); }  //Direct Console output at a particular coordinate. void ConPrintAt(int x, int y, char *CharBuffer, int len) {    DWORD count;    COORD coord = {x, y};    HANDLE hStdOut = GetStdHandle(STD_OUTPUT_HANDLE);    SetConsoleCursorPosition(hStdOut, coord);    WriteConsole(hStdOut, CharBuffer, len, &count, NULL); }  //Hides the console cursor void HideTheCursor() {    CONSOLE_CURSOR_INFO cciCursor;    HANDLE hStdOut = GetStdHandle(STD_OUTPUT_HANDLE);     if(GetConsoleCursorInfo(hStdOut, &cciCursor))    {       cciCursor.bVisible = FALSE; 	  SetConsoleCursorInfo(hStdOut, &cciCursor);    } }  //Shows the console cursor void ShowTheCursor() {    CONSOLE_CURSOR_INFO cciCursor;    HANDLE hStdOut = GetStdHandle(STD_OUTPUT_HANDLE);     if(GetConsoleCursorInfo(hStdOut, &cciCursor))    {       cciCursor.bVisible = TRUE; 	  SetConsoleCursorInfo(hStdOut, &cciCursor);    } }

引用 4 楼 iloveyou418 的回复:清屏，你现在看到的很多图像都是通过刷新来进行的，一帧一帧刷新。。。 你这个只需要数据产生变化才进行shuaxin1就可以了~前提是楼主的程序北京得做成图片

引用 2 楼 limitlessun 的回复:[quote=引用 1 楼 cfjtaishan 的回复:] 可以用清屏和重新输出的方法替换覆盖；这样实现比较简单；  现在的思路是在每次输出前调用system("cls"),请问可行吗?[/quote] 我想应该可行的。还是建议你试一下；

引用 1 楼 cfjtaishan 的回复:可以用清屏和重新输出的方法替换覆盖；这样实现比较简单；  现在的思路是在每次输出前调用system("cls"),请问可行吗?

可以用清屏和重新输出的方法替换覆盖；这样实现比较简单；


Question: 大一c语言问题

容易引起歧义的代码请用括号来进行分隔开，比如连续多个 ? :

c=a>b? ++a:++b; 其实可以拆分为： C=某某为最后执行 右边的为三元表达， 如果a大于b为真，返回a，++a会先计算，也就是返回的是a+1后的值 如果a小于吧，也就是a》b为假，返回吧，++b会先加1再返回b+1后的值，如果这个题变一下b++，就会先返回b，并不是返回b+1后的值。 然后c就算出来了

#include <stdio.h> int main() {     int a=5,b=4,c;     c = a > b ? ++a : ++b;     printf("%d %d %d\n",a,b,c);     c = (b-a? a+b:a-3)? b:a;     printf("%d %d %d\n",a,b,c);     return 0; }  如上的code输出结果是6 4 4，而不是6 4 10，因为加了括号，影响了表达式的运算优先级；自然，若是输出6 4 10原因是：  c=b-a? a+b:a-3? b:a; 表达式是从右向左运算，a - 3 位3，即非0，所以接下来运算c = b - a ? a + b ： b；最后的结果是a+b赋值给c，所以是10； 第二个打印b不是5，因为++b没有执行，a > b，那么会把++a的值赋值给c；所以++b没有执行；自然第二个打印b还是4；

1. a>b 真，所以c = ++a，而++b未求值，即a增一，b不变，c赋值为a的值（6） 2. 相当于：c = (b-a)? (a+b): (a-3? b:a); 先求值，再赋值，b-a真，求值a+b为10，赋值给c


Question: 做拓扑排序的时候出了问题!!求助

在必要位置设置断点，然后单步跟踪程序运行，观察变量变化情况与你期望的是否一致，分析原因，不要只是空想


Question: 字符串比较问题其扩展距离。

递归式： val(i,j)=min{val(i-1,j)+k,val(i,j-1)+k,val(i-1,j-1)+dist(a_i,b_j) 算法是递归的，程序实现是递推的，这是个公共的算法，建议自己先搜一下： http://blog.csdn.net/asce1885/article/details/5618788

百度搜相关关键字。  代码功能归根结底不是别人帮自己看或讲解或注释出来的；而是被自己静下心来花足够长的时间和精力亲自动手单步或设断点或对执行到某步获得的中间结果显示或写到日志文件中一步一步分析出来的。 提醒：再牛×的老师也无法代替学生自己领悟和上厕所！ 单步调试和设断点调试（VS IDE中编译连接通过以后，按F10或F11键单步执行，按Shift+F11退出当前函数；在某行按F9设断点后按F5执行停在该断点处。）是程序员必须掌握的技能之一。


Question: 一段小程序运行出错，求大神帮忙看看

引用 2 楼 cfjtaishan 的回复:看不懂你的计算逻辑， int index=abs(nums[i])-1;         if(nums[index]<0) 这样用index不会越界吗？ 比如这样输入：  5 100 200 300 400 100  这样必定会越界的。  所以，你的算法应该有问题； 数组里的数是小于数组长度的，不好意思忘记说了

出错时中断下来，通过调用堆栈定准到相关位置，分析原因，必要时，在相关位置设置断点，然后单步跟踪程序运行，观察变量变化情况，查掉是否越界，是否访问了无效指针等

边界条件 输入输出格式 ……


Question: 关于C++使用指针函数转置二维数组的问题

麻烦看一下还是不对

挖空题。楼上正确。

j<n   *(*(p + i) + j)=*(*(p +j) +i);             *(*(p + j) +i)=t;  p,3,4

http://edu.csdn.net/course/detail/2516 C语言指针与汇编内存地址-三.数组和二维数组


Question: C语言描述顺序表

看起来你的基本概念都没掌握，回去重新好好看书吧。

引用 2 楼 cfjtaishan 的回复:#include <stdio.h> #include <stdlib.h> #include <time.h>  #define MAXSIZE 100  typedef int ElemType;  typedef struct {     ElemType data[MAXSIZE];     int length; }Sqlist;   void swap(ElemType &a, ElemType &b) {     ElemType c;     c = a;     a = b;     b = c; }  void divide(Sqlist *&L) {     int i = 0;     int j = L->length-1;     int temp = 0;      while(1)     {         for (; i < L->length; i++)             if (L->data[i] % 2 == 0)                 break;          for (; j > i; j--)             if (L->data[j] % 2 == 1)                 break;          if (i < j)             swap(L->data[i], L->data[j]);         else             break;          /*         if((L->data[i]%2)==0)         {             temp = L->data[i];         }         else         {             i++;         }         if((L->data[j]%2)==1)         {             L->data[i] = L->data[j];             L->data[j] = temp;         }         else         {             j--;         }         */     } }  void print_list(Sqlist *s) {     int i;      for(i=0; i< s->length; i++)         printf("%d ", s->data[i]);     putchar(10); }  int main() {     Sqlist *L, s;     int n, i;     printf("Input the number of list: ");     scanf("%d", &n);     if (n > MAXSIZE)         return 0;     L = &s;     srand(time(NULL));     for (i = 0; i < n; i++)         L->data[i] = rand() % 100;     L->length = n;      printf("Before swap: \n");     print_list(L);     divide(L);     printf("After swap: \n");     print_list(L);     return 0 ; }  参考一下吧  L->length不能直接通过sizeof获得，因为sizeof得到的是MAXSIZE，但是实际上没有那么多数据。所以，采用输入的形式； 分类函数也有点逻辑问题，上面的代码供参考； 好的，谢谢