假设我正在运行一个脚本(例如Python)。为了找出程序花了多长时间,可以运行
time python script1.py
是否有一个命令可以跟踪脚本运行时使用了多少 RAM?为了查找有多少 RAM 可用,可以使用free
,但此命令不适合上述任务。
答案1
这时间(1)命令(您可能需要安装它 - 也许作为time
包 - ,它应该在 中/usr/bin/time
)接受许多参数,包括可以理解(除其他外)的格式字符串(带有-f
或--format
)
%M Maximum resident set size of the process during its lifetime,
in Kbytes.
%K Average total (data+stack+text) memory use of the process, in
Kbytes.
不要将该/usr/bin/time
命令与time
bash 内置。您可能需要输入完整的文件路径/usr/bin/time
(以要求您的 shell 运行命令不是内置的)或类型command time
或\time
(感谢托比·斯佩特& 到箭征求他们的意见)。
所以你可以尝试(RSS 是常驻集大小)
/usr/bin/time -f "mem=%K RSS=%M elapsed=%E cpu.sys=%S user=%U" python script1.py
你也可以尝试
/usr/bin/time --verbose python script1.py
你问的是:
脚本运行时使用了多少 RAM?
这表明你有一个误解。在 Linux(或任何现代多进程操作系统)上运行的应用程序正在使用虚拟内存,以及每个过程(包括python
运行脚本的进程)有自己的虚拟地址空间。进程不运行直接地在身体的RAM,但有自己的虚拟地址空间(并在其中运行),内核通过复杂的方式实现虚拟内存请求寻呼使用懒惰写时复制技术并配置内存管理单元。这内存是使用和管理的物理设备和资源内部由内核 - 实现虚拟内存(另请参阅页面缓存以及关于殴打)。
您可能需要花几天时间了解更多操作系统。我推荐阅读操作系统:三个简单的部分这是一本可免费下载的书。 RAM 由整个操作系统使用(不是直接由各个进程使用),并且给定进程的 RAM 中的实际页面可能会随时间而变化(并且可能以某种方式与其他进程共享)。因此,给定进程的 RAM 消耗没有明确定义,因为它不断变化(您可能需要其平均值或峰值等......),并且其虚拟地址空间的大小也是如此。
您还可以使用(特别是如果您的脚本运行几秒钟)顶部(1)实用程序(也许在其他一些终端中),或者附注(1)或者映射(1)-也许使用手表(1)重复该命令ps
或pmap
命令。您甚至可以直接使用/proc/
(参见过程(5)...)也许作为watch cat /proc/$(pidof python)/status
或/proc/$(pidof python)/stat
或/proc/$(pidof python)/maps
等等...
但内存使用情况(由某些进程的内核)是广泛随时间变化对于给定的进程(甚至其虚拟地址空间也在变化,例如通过调用映射(2)并被munmap
使用ld-linux(8),dlopen(3),分配(3)&free
以及 Python 解释器所需的许多其他函数...)。
你也可以使用跟踪(1)去了解系统调用由 Python 为你的脚本完成(所以你会理解它如何使用mmap
&munmap
和其他系统调用(2)). 您可以strace
使用-e trace=%memory
或-e trace=memory
来限制仅获取与内存(即虚拟地址空间)相关的系统调用。
顺便说一句,跟踪内存分配Python 功能也可能很有用。
我猜可能是你仅有的关心虚拟记忆,这是关于虚拟地址空间(但不是关于 RAM),Python 解释器使用它来运行 Python 脚本。这在流程执行过程中正在发生变化。 RSS(或虚拟地址空间的最大峰值大小)实际上可能更有用。
也可以看看LinuxAteMyRAM。
答案2
还可以使用传说中的valgrind
,尽管您可能需要从包管理器安装它。
$ valgrind c-projects/objtest/bin/objtest
==6543== Memcheck, a memory error detector
==6543== Copyright (C) 2002-2015, and GNU GPL'd, by Julian Seward et al.
==6543== Using Valgrind-3.12.0.SVN and LibVEX; rerun with -h for copyright info
==6543== Command: c-projects/objtest/bin/objtest
==6543==
|ERROR|array:189: array_delete: delete index 0 but the highest is -1 (delete from empty array): index out of bounds
==6543==
==6543== HEAP SUMMARY:
==6543== in use at exit: 480 bytes in 20 blocks
==6543== total heap usage: 7,390 allocs, 7,370 frees, 256,217 bytes allocated
==6543==
==6543== LEAK SUMMARY:
==6543== definitely lost: 96 bytes in 4 blocks
==6543== indirectly lost: 384 bytes in 16 blocks
==6543== possibly lost: 0 bytes in 0 blocks
==6543== still reachable: 0 bytes in 0 blocks
==6543== suppressed: 0 bytes in 0 blocks
==6543== Rerun with --leak-check=full to see details of leaked memory
==6543==
==6543== For counts of detected and suppressed errors, rerun with: -v
==6543== ERROR SUMMARY: 0 errors from 0 contexts (suppressed: 0 from 0)
如果您是高级用户并且想要精美的图表,您可以使用ms_print
如下命令:
valgrind --tool=massif --pages-as-heap=yes --massif-out-file=massif.out ./test.sh; grep mem_heap_B massif.out | sed -e 's/mem_heap_B=\(.*\)/\1/' | sort -g | tail -n 1
答案3
可以使用pmap命令查看进程使用的内存量。在您的情况下,您需要将脚本的 PID 作为 pmap 命令的输入,例如
pmap $(ps -ef | grep **<SCRIPT NAME>** | grep -v grep | awk '{print $2}')