首页 新闻 会员 周边 捐助

关于System.StackOverflowException的问题

0
悬赏园豆:50 [已解决问题] 解决于 2012-08-15 17:48

/// <summary>
        /// 文本记录
        /// </summary>
        /// <param name="msg">文本信息</param>
        /// <param name="type">1错误日志 2运行日志</param>
        public static void LogText(string msg,int type)
        {
            lock (obj)
            {
                System.Text.StringBuilder str = new System.Text.StringBuilder();
                str.Append(DateTime.Now.ToString() + ":");
                str.Append(msg);
                str.Append("\n");
                if (!Directory.Exists(AppDomain.CurrentDomain.BaseDirectory + "Log"))
                    Directory.CreateDirectory(AppDomain.CurrentDomain.BaseDirectory + "Log");
                string FilePath;
                if (type == 1)
                    FilePath = AppDomain.CurrentDomain.BaseDirectory + "Log\\err_" + DateTime.Now.ToString("yyyyMMdd") + ".txt";
                else if(type==2)
                    FilePath = AppDomain.CurrentDomain.BaseDirectory + "Log\\run_" + DateTime.Now.ToString("yyyyMMdd") + ".txt";
                else
                    FilePath = AppDomain.CurrentDomain.BaseDirectory + "Log\\cf_" + DateTime.Now.ToString("yyyyMMdd") + ".txt";
                System.IO.StreamWriter sw = null;
                try
                {
                    if (!System.IO.File.Exists(FilePath))
                    {
                        System.IO.FileStream fs = System.IO.File.Create(FilePath);
                        fs.Close();
                    }
                    sw = new System.IO.StreamWriter(FilePath, true, System.Text.Encoding.Default);
                    sw.Write(str.ToString());
                }
                catch (Exception ex)
                {
                }
                finally
                {
                    if (sw != null)
                        sw.Close();
                }
            }
        }

 

一个写日志的方法。软件运行久了就会在“sw = new System.IO.StreamWriter(FilePath, true, System.Text.Encoding.Default);”这句报System.StackOverflowException的异常。

System.StackOverflowException往往是出现无限制的递归导致的,函数调用层次过多导致栈溢出。而该代码应该没有递归之类的。

请达人帮忙分析一下,该代码问题所在

寒风吹过的主页 寒风吹过 | 初学一级 | 园豆:149
提问于:2012-08-08 17:12
< >
分享
最佳答案
0

看这个方法并无不妥。

不过基于“StackOverflowException”的异常,请楼主仔细检查一下上下文代码,严重怀疑外围代码有大量递归逻辑处理,导致堆栈溢出。

如果有大量递归请改为循环。

收获园豆:15
基本原则 | 初学一级 |园豆:64 | 2012-08-10 12:28

的确是外围有大量的递归,递归没完,GC不会回收,导致占用了大量内存,从而导致溢出。(只是很奇怪为什么每次报错都报在new StreamWriter哪里?)

改成了循环就好了。

寒风吹过 | 园豆:149 (初学一级) | 2012-08-15 17:50
其他回答(4)
0

既然无法查大错误原因,就将这个方法给换成log4net来记录日志

收获园豆:5
az235 | 园豆:8483 (大侠五级) | 2012-08-09 08:17
0

把方法的static去掉……

收获园豆:15
需要格局 | 园豆:2145 (老鸟四级) | 2012-08-09 12:29

原理?

支持(0) 反对(0) 寒风吹过 | 园豆:149 (初学一级) | 2012-08-09 12:58

@寒风吹过: 

先试试!!我看你的这个异常是“堆栈溢出”的异常……由于我想到了问题可能静态方法这里的问题……

支持(0) 反对(0) 需要格局 | 园豆:2145 (老鸟四级) | 2012-08-09 13:05

@田麦成: 

static去掉,那就是把静态方法改成实例方法了?那每次调用是重新一个实例呢(这样很耗),还是程序启动生成一次实例(这样感觉跟静态方法也没啥区别?都是常驻内存)

另外说一下。程序是一般是运行3个小时以上才开始异常。初步估计这个日志方法会调个几W次吧。

支持(0) 反对(0) 寒风吹过 | 园豆:149 (初学一级) | 2012-08-09 18:09

@寒风吹过: 

静态方法,内部还有lock锁……这两个地方导致的问题……

支持(0) 反对(0) 需要格局 | 园豆:2145 (老鸟四级) | 2012-08-09 18:26
0

楼主,应该好好的检查 为何 会出现 “出现无限制的递归导致”?

 

还有这个 “ System.IO.FileStream fs

这个你也应该在try 外面定义,然后再finally中判断如果不为null,就调用dispose方法。

收获园豆:15
chenping2008 | 园豆:9836 (大侠五级) | 2012-08-09 13:55

System.IO.FileStream fs这个应该没关系。后来检查发现这段代码是多余的,已经去掉了

可还是出现这个问题。

支持(0) 反对(0) 寒风吹过 | 园豆:149 (初学一级) | 2012-08-09 18:05

@寒风吹过: LogText 这个方法本身不是递归的调用,那它是不是在其他的递归的调用里面呢?

如果完全没有递归的调用,那怎么会有这样的错误呢?

看了下,这个streamwriter 这个构造函数中的所有的异常:

// 异常:
        //   System.UnauthorizedAccessException:
        //     访问被拒绝。
        //
        //   System.ArgumentException:
        //     path 为空。- 或 -path 包含系统设备的名称(com1、com2 等等)。
        //
        //   System.ArgumentNullException:
        //     path 为 null。
        //
        //   System.IO.DirectoryNotFoundException:
        //     指定的路径无效,比如在未映射的驱动器上。
        //
        //   System.IO.IOException:
        //     path 包含不正确或无效的文件名、目录名或卷标的语法。
        //
        //   System.IO.PathTooLongException:
        //     指定的路径、文件名或者两者都超出了系统定义的最大长度。例如,在基于 Windows 的平台上,路径必须小于 248 个字符,文件名必须小于 260
        //     个字符。
        //
        //   System.Security.SecurityException:
        //     调用方没有所要求的权限。

根本没有提到 StackOverflowException 异常。

支持(0) 反对(0) chenping2008 | 园豆:9836 (大侠五级) | 2012-08-10 16:12
0

hghghghghgh

随碟附送520 | 园豆:206 (菜鸟二级) | 2016-08-17 10:54
清除回答草稿
   您需要登录以后才能回答,未注册用户请先注册