我刚刚发现我的脚本给了我一个致命的错误:
Fatal error: Allowed memory size of 268435456 bytes exhausted (tried to allocate 440 bytes) in C:\process_txt.php on line 109
Run Code Online (Sandbox Code Playgroud)
那条线是这样的:
$lines = count(file($path)) - 1;
Run Code Online (Sandbox Code Playgroud)
所以我认为将文件加载到记忆中并计算行数很困难,是否有更有效的方法可以做到这一点而不会出现内存问题?
我需要计算的行数为2MB到500MB的文本文件.也许有时候是Gig.
谢谢大家的帮助.
"泄漏抽象"一词是什么意思?(请用例子解释.我经常很难完成一个理论.)
memory-leaks abstraction programming-languages functional-programming leaky-abstraction
这是从这个布拉德·拉尔森的答案 SO问题
如果添加两个断点,则应该能够调试这些异常.为此,请转到"运行"| 显示| 断点并创建两个全局断点(我在全局中断点,因为它们在我的所有应用程序中都非常有用).第一个应命名为"objc_exception_throw",其位置应为"libobjc.A.dylib".第二个应该是" - [NSException raise]",它的位置应该是"CoreFoundation".
现在,如果您在启用断点的情况下开始调试应用程序,它应该在抛出这些异常时中断.然后,您应该能够在调试器中看到导致异常的事件链.
现在在这个答案中我想问我如何添加位置提到???
这是我一直试图追踪几个月的问题.我有一个运行java应用程序来处理xml提要并将结果存储在数据库中.存在非常难以追踪的间歇性资源问题.
背景: 在生产盒(问题最明显的地方),我没有特别好的访问框,并且无法运行Jprofiler.那个盒子是64位四核,8GB机器运行centos 5.2,tomcat6和java 1.6.0.11.它从这些java-opts开始
JAVA_OPTS="-server -Xmx5g -Xms4g -Xss256k -XX:MaxPermSize=256m -XX:+PrintGCDetails -
XX:+PrintGCTimeStamps -XX:+UseConcMarkSweepGC -XX:+PrintTenuringDistribution -XX:+UseParNewGC"
Run Code Online (Sandbox Code Playgroud)
技术堆栈如下:
我能解决的最接近问题的是32位机器,内存要求较低.我确实有控制权.我已经使用JProfiler探测它并修复了许多性能问题(同步问题,预编译/缓存xpath查询,减少了线程池,删除了不必要的hibernate预取,以及在处理过程中过度热心的"缓存变暖").
在每种情况下,分析器都会将这些资源显示为由于某种原因而占用大量资源,并且一旦发生变化,这些资源就不再是主要资源.
问题: JVM似乎完全忽略了内存使用设置,填满了所有内存并且没有响应.对于面向客户的人来说,这是一个问题,他们期望定期投票(5分钟和1分钟重试),以及我们的运营团队,他们经常被告知箱子已经无响应并且必须重新启动它.这个盒子上没有其他重要的东西.
问题似乎是垃圾收集.我们正在使用ConcurrentMarkSweep(如上所述)收集器,因为原始STW收集器导致JDBC超时并变得越来越慢.日志显示,随着内存使用量的增加,这开始引发cms失败,并回到最初的世界收藏家,然后似乎没有正确收集.
然而,运行jprofiler,"运行GC"按钮似乎很好地清理内存而不是显示增加的占用空间,但由于我无法将jprofiler直接连接到生产盒,并且解决已证实的热点似乎无法正常工作我是留下了调整垃圾收集盲人的伏都教.
我尝试过的:
不幸的是,问题也偶尔会出现,它似乎是不可预测的,它可以运行几天甚至一周而没有任何问题,或者它可以在一天内失败40次,而且我唯一可以看到的是一致的是垃圾收集正在起作用.
任何人都可以提出以下建议:
a)为什么JVM在配置为最大值小于6时使用8个物理演出和2 gb交换空间
.b)对GC调整的引用实际上解释或给出了合理的示例什么样的设置使用高级集合.
c)对最常见的java内存泄漏的引用(我理解无人认领的引用,但我的意思是在库/框架级别,或者在数据结构中更像inherenet,比如hashmaps).
感谢您提供的任何和所有见解.
编辑
Emil H:
1)是的,我的开发集群是生产数据的镜像,直到媒体服务器.主要的区别是32/64bit和可用的RAM量,我无法轻易复制,但代码和查询和设置是相同的.
2)有一些遗留代码依赖于JaxB,但在重新排序作业以试图避免调度冲突时,我通常会删除执行,因为它每天运行一次.主解析器使用调用java.xml.xpath包的XPath查询.这是一些热点的来源,其中一个查询没有被预编译,两个对它们的引用都是硬编码的字符串.我创建了一个线程安全缓存(hashmap),并将对xpath查询的引用考虑为最终的静态字符串,从而显着降低了资源消耗.查询仍然是处理的很大一部分,但应该是因为这是应用程序的主要责任.
3)另外一个注释,另一个主要消费者是来自JAI的图像操作(从饲料中重新处理图像).我不熟悉java的图形库,但从我发现它们并没有特别漏洞.
(感谢目前为止的答案,伙计们!)
更新:
我能够使用VisualVM连接到生产实例,但它已禁用GC可视化/运行GC选项(尽管我可以在本地查看).有趣的是:VM的堆分配服从JAVA_OPTS,并且实际分配的堆正好坐在1-1.5 gigs,并且似乎没有泄漏,但是盒级监控仍显示泄漏模式,但它是没有反映在VM监控中.这个盒子上没有别的东西在跑,所以我很难过.
为什么Eclipse会让我变暖"资源泄漏:'in'永远不会关闭"以下代码?
public void readShapeData() {
Scanner in = new Scanner(System.in);
System.out.println("Enter the width of the Rectangle: ");
width = in.nextDouble();
System.out.println("Enter the height of the Rectangle: ");
height = in.nextDouble();
Run Code Online (Sandbox Code Playgroud) 以下是事实:
语言Go有一个垃圾收集器.
Java有一个垃圾收集
很多Java程序都有(细微的或没有)内存泄漏
作为一个有内存泄漏的Java程序的例子(不是为了胆小的人,这个问题可能会动摇你的信念),请看这里有一个叫做Tomcat的小程序,它甚至有一个"查找泄漏"按钮:有没有办法为了避免Tomcat中的部署内存泄漏?
所以我想知道:用Go编写的程序是否会出现与Java编写的某些程序相同的(细微的或不存在的)内存泄漏?
我最近在CppCon 2016上观看了Herb Sutter关于"Leak Free C++ ..."的精彩演讲,他谈到了使用智能指针实现RAII(资源获取是初始化) - 概念以及它们如何解决大多数内存泄漏问题.
现在我在想.如果我严格遵循RAII规则,这似乎是一件好事,为什么这与C++中的垃圾收集器有什么不同呢?我知道使用RAII,程序员可以完全控制何时再次释放资源,但是在任何情况下都只对垃圾收集器有益吗?它的效率真的会降低吗?我甚至听说有一个垃圾收集器可以更高效,因为它可以一次释放更大的内存块,而不是在代码中释放小内存块.
我在 MacOS Mojave 上运行 docker 桌面社区 2.1.0.3。我已经为 Docker 分配了 8GB 的内存,这看起来已经很多了(这是我 RAM 的一半)。不知何故,即使在退出然后再次启动 Docker for Mac(这意味着没有容器正在运行)之后,docker 已经超过了 1GB 的内存分配。
没有容器运行的 docker 的预期内存使用量是多少?docker for mac 或 docker's hyperkit 中是否存在内存泄漏?
我有一个例程,每秒多次对SQLite数据库运行不同的查询.过了一会儿,我会得到错误
"android.database.CursorWindowAllocationException: - Cursor window allocation of 2048 kb failed. # Open Cursors = "
出现在LogCat中.
我有应用程序日志内存使用情况,实际上当使用率达到一定限度时,我收到此错误,暗示它用完了.我的直觉告诉我,每次运行查询时数据库引擎都在创建一个新缓冲区(CursorWindow),即使我将.close()标记为游标,垃圾收集器也SQLiteDatabase.releaseMemory()
不足以释放内存.我认为解决方案可能在于"强制"数据库始终写入相同的缓冲区,而不是创建新的缓冲区,但我一直无法找到这样做的方法.我已经尝试实例化我自己的CursorWindow,并尝试将其设置为和SQLiteCursor无济于事.
有任何想法吗?
编辑:来自@GrahamBorland的示例代码请求:
public static CursorWindow cursorWindow = new CursorWindow("cursorWindow");
public static SQLiteCursor sqlCursor;
public static void getItemsVisibleArea(GeoPoint mapCenter, int latSpan, int lonSpan) {
query = "SELECT * FROM Items"; //would be more complex in real code
sqlCursor = (SQLiteCursor)db.rawQuery(query, null);
sqlCursor.setWindow(cursorWindow);
}
Run Code Online (Sandbox Code Playgroud)
理想情况下,我希望能够.setWindow()
在提供新查询之前,CursorWindow
每次获取新数据时都将数据放入相同的数据中.
我有一个.NET服务,其正常的私有工作集大约为80 MB.在最近的负载测试期间,进程达到3.5 GB内存使用量,导致整个机器的物理内存不足(使用4 GB中的3.9),并且在负载测试停止后很长时间内内存未释放.使用任务管理器,我获取了该进程的转储文件并在Visual Studio 2010 SP1中打开它,我可以开始调试它.
我如何诊断内存问题?我有dotTrace Memory 3.x,它是否支持转储文件的内存分析?如果没有,Visual Studio 2010 Premium的内存分析功能是否有帮助(我目前有专业版)?WinDbg可以帮忙吗?
更新:新的Visual Studio 2013 Ultimate现在可以使用转储文件本机诊断内存问题.有关详细信息,请参阅此博客文章.
.net memory-leaks crash-dumps visual-studio-2010 memory-profiling