【有效解决】C# 报错System.StackOverflowException

报错原因: 因为使用了递归,当调用的深度过深,则会引发内存溢出从而触发.net的保护机制,导致程序中断

经过两天的奋战,终于完美解决了这个问题,接下来Share一下我的解决过程,没有耐心看的可以直接滑到底部,查看最终的解决方案。

详细报错信息截图:
在这里插入图片描述
----------解决过程分享----------

在网上冲浪找了很久,总结了一下网友们提供的两个解决方案,为:

1.使用Thread.Sleep(1000)
我使用后的结论: 除了会降低递归的速度以外,并没有其他帮助,未能解决问题。递归到一定的量,占用足够的内存时照样会提示报错System.StackOverflowException。

2.改变递归的写法
原先的递归写法:

public void MethodA()
{
    if () 
    {
    }
    else
    {
        this.MethodA();
    }
}

改为:

public void MethodA()
{
    if () 
    {
    }
    else
    {
        this.MethodB();
    }
}

public void MethodB()
{
    if ()
    {
    }
    else
    {
        MethodA();
    }
}

他对这两种的写法解释为:比较两种写法,第一种写法不断的递归,函数嵌套层数过多最后导致栈内存溢出,而第二种写法将循环的部分放到了另外一个函数,进入MethodB的时候MethodA已经结束了,其占用的栈内存可以得到释放,所以没有过多的函数嵌套。
我使用后的结论: 除了实现递归的写法变得复杂以外,并没有其他帮助,未能解决问题。递归到一定的量,占用足够的内存时照样会提示报错System.StackOverflowException。

----------最终的解决方案----------
在你调用递归的方法那里,加入两行代码,最终代码:

private int iQty = 0;

public void MethodA()
{
    if () 
    {
    }
    else
    {
        this.MethodB();
    }
}

public void MethodB()
{
    if ()
    {
    }
    else
    {
	    iQty++;
	    if(iQty % 10 == 0)
	    {
	    	//这里加多一个判断,每当循环十次后,就使用新线程的方式来调用方法,主要是为了释放之前的内存,避免内存溢出。
	        var t = new Thread(delegate () { MethodA(); }, 1073741824);
			t.Start();
		}
		else
		{
			MethodA();
		}
    }
}

MethodA() --> 递归调用的方法
1073741824 --> 最大堆栈大小

运行后,测试,完美解决!!!

加入这两行代码的作用: 实例化开启新的线程并委托递归调用的方法,这样就能和之前的进程分离,释放之前线程占用的内存。指定新的线程最大堆栈大小,防止递归调用的方法会内存溢出。

评论 6
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值