关于单精度实数和双精度实数的取位有关问题

关于单精度实数和双精度实数的取位问题
#include<stdio.h>

int main(void)
{
int k;
for(k=2;k<6;k++,k++)
printf("##%d\n",k);

printf("\n从键盘上依次输入一个整数,单精度实数,一个双精度实数,一个数字字符(用逗号隔开):\n");
printf("2,2.5,3.1415926,8\n\n");

int a=2;
float b=2.5;
double c=3.1415926,  sum;
char d='8';
sum=a+b+c+d;
printf("整数为:%d,单精度实数为:%f,双精度实数为:%lf,数字字符为:%c,\n和为:%lf\n",a,b,c,d,sum);



return 0;
}


我想问的是:
    
 运行后,为什么双精度反而还舍去一位小数从3.1415926变到3.141593了。
(double不是有15~16位有效数字吗?)

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