<?xml version="1.0" encoding="utf-8" standalone="yes"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom">
  <channel>
    <title>Instruments on Swift Dev Journal</title>
    <link>https://swiftdevjournal.com/tags/instruments/</link>
    <description>Recent content in Instruments on Swift Dev Journal</description>
    <generator>Hugo</generator>
    <language>en-us</language>
    <lastBuildDate>Mon, 10 Aug 2026 13:23:46 -0400</lastBuildDate>
    <atom:link href="https://swiftdevjournal.com/tags/instruments/index.xml" rel="self" type="application/rss+xml" />
    <item>
      <title>Using Top Functions Mode in Instruments to Quickly Find the Slowest Code</title>
      <link>https://swiftdevjournal.com/posts/top-functions/</link>
      <pubDate>Mon, 10 Aug 2026 13:23:46 -0400</pubDate>
      <guid>https://swiftdevjournal.com/posts/top-functions/</guid>
      <description>&lt;p&gt;In Xcode 26.4 Apple added a Top Functions mode to the Time Profiler and CPU Profiler instruments to help you quickly find the functions where your app spends the most time. This article explains the Top Functions mode.&lt;/p&gt;&#xA;&lt;p&gt;If you are new to time profiling with Instruments, read the following article:&lt;/p&gt;&#xA;&lt;p&gt;&lt;a href=&#34;https://swiftdevjournal.com/posts/cpu-profiler/&#34;&gt;Find the Slow Spots in Your Code with the CPU Profiler Instrument&lt;/a&gt;&lt;/p&gt;&#xA;&lt;p&gt;The article covers the CPU Profiler instrument, but the material also applies to the Time Profiler instrument.&lt;/p&gt;&#xA;&lt;h2 id=&#34;switch-to-top-functions-mode&#34;&gt;Switch to Top Functions Mode&lt;/h2&gt;&#xA;&lt;p&gt;Above the detail view is a set of three buttons.&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;Top Functions button&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/InstrumentsTopFunctionsButton.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;Click the right button (highlighted in blue in the screenshot) to switch to Top Functions mode.&lt;/p&gt;&#xA;&lt;p&gt;The Top Functions mode sorts the call tree by the Self Weight column (Self Cycles in the CPU Profiler instrument) so the functions where your app spends the most time appear at the top of the call tree. Double-click a function you wrote to find the lines of code where your app spends the most time.&lt;/p&gt;&#xA;&lt;h2 id=&#34;flame-graph&#34;&gt;Flame Graph&lt;/h2&gt;&#xA;&lt;p&gt;Selecting a function from the call tree view shows a flame graph of the code paths that called the function. Focusing on a single function makes the Top Functions flame graph easier to read than reading the complete flame graph.&lt;/p&gt;&#xA;&lt;p&gt;If you have never used Instruments flame graphs, the following article provides an introduction to them:&lt;/p&gt;&#xA;&lt;p&gt;&lt;a href=&#34;https://swiftdevjournal.com/posts/instruments-flame-graph-intro/&#34;&gt;Instruments Flame Graph Introduction&lt;/a&gt;&lt;/p&gt;&#xA;&lt;p&gt;Above the flame graph are two buttons. The left button, Callers, shows the default flame graph view. The default view shows the call stack in reverse, with the selected function at the bottom of the graph. The right button, Inverted Callees, inverts the flame graph.&lt;/p&gt;&#xA;&lt;h2 id=&#34;do-you-want-to-learn-more-about-instruments&#34;&gt;Do you want to learn more about Instruments?&lt;/h2&gt;&#xA;&lt;p&gt;I wrote a book, &lt;em&gt;Profiling Swift Apps&lt;/em&gt;, that shows you how to use Instruments to find and fix problems in your code. The book will help you make apps that run faster and use less memory. You can learn more about the book and download a sample at the following link:&lt;/p&gt;&#xA;&lt;p&gt;&lt;a href=&#34;https://swiftdevjournal.com/instruments-book/&#34;&gt;Profiling Swift Apps page&lt;/a&gt;&lt;/p&gt;&#xA;</description>
    </item>
    <item>
      <title>Measure App Launch Time with Instruments</title>
      <link>https://swiftdevjournal.com/posts/measure-app-launch-time/</link>
      <pubDate>Tue, 10 Feb 2026 12:34:53 -0500</pubDate>
      <guid>https://swiftdevjournal.com/posts/measure-app-launch-time/</guid>
      <description>&lt;p&gt;Take the following steps to measure your app&amp;rsquo;s launch time with Instruments:&lt;/p&gt;&#xA;&lt;ol&gt;&#xA;&lt;li&gt;Press Cmd-I or choose Product &amp;gt; Profile to profile your app.&lt;/li&gt;&#xA;&lt;li&gt;Select the App Launch template when Instruments launches.&lt;/li&gt;&#xA;&lt;li&gt;Click the Choose button.&lt;/li&gt;&#xA;&lt;li&gt;Click the Record button to start profiling.&lt;/li&gt;&#xA;&lt;li&gt;Select the item with the name of your app from the timeline pane.&lt;/li&gt;&#xA;&lt;li&gt;Press Cmd-4 to open the App Lifecycle section.&lt;/li&gt;&#xA;&lt;/ol&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;App Lifecycle Section&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/AppLifecycle.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;The App Lifecycle section lists the app&amp;rsquo;s launch steps and how long each step took.&lt;/p&gt;&#xA;&lt;h2 id=&#34;do-you-want-to-learn-more-about-instruments&#34;&gt;Do you want to learn more about Instruments?&lt;/h2&gt;&#xA;&lt;p&gt;I wrote a book, &lt;em&gt;Profiling Swift Apps&lt;/em&gt;, that shows you how to use Instruments to find and fix problems in your code. The book will help you make apps that run faster and use less memory. You can learn more about the book and download a sample at the following link:&lt;/p&gt;&#xA;&lt;p&gt;&lt;a href=&#34;https://swiftdevjournal.com/instruments-book/&#34;&gt;Profiling Swift Apps page&lt;/a&gt;&lt;/p&gt;&#xA;</description>
    </item>
    <item>
      <title>Find the SwiftUI Views that Update the Most Using Instruments</title>
      <link>https://swiftdevjournal.com/posts/swiftui-frequent-view-updates/</link>
      <pubDate>Mon, 03 Nov 2025 12:44:02 -0400</pubDate>
      <guid>https://swiftdevjournal.com/posts/swiftui-frequent-view-updates/</guid>
      <description>&lt;p&gt;When profiling a SwiftUI app with Instruments, one thing you want to know is what views update the most. If a view updates more than you expect, you want to know what causes the updates. In this article you will learn how to use the SwiftUI instrument to find the views in your app that update the most and find what triggers view updates.&lt;/p&gt;&#xA;&lt;p&gt;This article uses the new SwiftUI instrument Apple added in Xcode 26. If you are using an earlier version of Xcode, read the following article:&lt;/p&gt;&#xA;&lt;p&gt;&lt;a href=&#34;https://swiftdevjournal.com/posts/swiftui-instruments/&#34;&gt;See How Many Times Your SwiftUI Views Redraw Using Instruments&lt;/a&gt;&lt;/p&gt;&#xA;&lt;h2 id=&#34;profile-your-app&#34;&gt;Profile your app&lt;/h2&gt;&#xA;&lt;p&gt;Take the following steps to profile your app with the SwiftUI instrument:&lt;/p&gt;&#xA;&lt;ol&gt;&#xA;&lt;li&gt;Go to Xcode.&lt;/li&gt;&#xA;&lt;li&gt;Press Cmd-I or choose Product &amp;gt; Profile to build your project and launch Instruments.&lt;/li&gt;&#xA;&lt;li&gt;Choose SwiftUI from the template list.&lt;/li&gt;&#xA;&lt;li&gt;Click the Choose button.&lt;/li&gt;&#xA;&lt;li&gt;Click the Record button above the sidebar to start profiling.&lt;/li&gt;&#xA;&lt;li&gt;Click the Stop button when you are finished.&lt;/li&gt;&#xA;&lt;/ol&gt;&#xA;&lt;h2 id=&#34;find-the-views-that-update-the-most&#34;&gt;Find the views that update the most&lt;/h2&gt;&#xA;&lt;p&gt;Use the all updates summary to find the views that update the most. Instruments should show the all updates summary when you stop profiling, but if you don&amp;rsquo;t see it in the detail view, press Cmd-1 or choose Summary: All Updates from the jump bar menu.&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;All Updates Summary&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/AllUpdatesSummary.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;The SwiftUI instrument&amp;rsquo;s all updates summary shows the following statistics for the views in your app:&lt;/p&gt;&#xA;&lt;ul&gt;&#xA;&lt;li&gt;Number of updates&lt;/li&gt;&#xA;&lt;li&gt;Total update time&lt;/li&gt;&#xA;&lt;li&gt;Shortest update&lt;/li&gt;&#xA;&lt;li&gt;Longest update&lt;/li&gt;&#xA;&lt;li&gt;Average update time&lt;/li&gt;&#xA;&lt;/ul&gt;&#xA;&lt;p&gt;Take the following steps to find the views that update the most:&lt;/p&gt;&#xA;&lt;ol&gt;&#xA;&lt;li&gt;Click the disclosure triangle next to the name of your app to see the app&amp;rsquo;s modules.&lt;/li&gt;&#xA;&lt;li&gt;Click the disclosure triangle next to your app&amp;rsquo;s module to see a list of your app’s views.&lt;/li&gt;&#xA;&lt;li&gt;Click the Count column heading to sort the views by update count so you can see what views update the most.&lt;/li&gt;&#xA;&lt;/ol&gt;&#xA;&lt;h2 id=&#34;find-what-causes-a-view-to-update&#34;&gt;Find what causes a view to update&lt;/h2&gt;&#xA;&lt;p&gt;Use the cause and effect graph in the SwiftUI instrument to find the cause of view updates. Take the following steps to show the cause and effect graph for a view:&lt;/p&gt;&#xA;&lt;ol&gt;&#xA;&lt;li&gt;Move the pointer over a view in the all updates summary.&lt;/li&gt;&#xA;&lt;li&gt;Click the small button that appears next to the name of the view.&lt;/li&gt;&#xA;&lt;li&gt;Choose Show Cause &amp;amp; Effect Graph.&lt;/li&gt;&#xA;&lt;/ol&gt;&#xA;&lt;p&gt;The cause and effect graph looks similar to the following screenshot:&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;Cause and Effect Graph&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/CauseAndEffectGraph.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;The graph consists of a collection of nodes with arrows showing the flow of events. Graph nodes for your code are blue. System-defined nodes are gray.&lt;/p&gt;&#xA;&lt;p&gt;Initially the graph is focused on the view you selected from the summary. The nodes to the left of the view show the events that trigger the view update. The nodes to the right of the view show the effects of the view update.&lt;/p&gt;&#xA;&lt;p&gt;To figure out what triggers an update, move left along the graph until you find other blue nodes. The most common cause of view updates is data updates. When the data the view shows changes, the view updates.&lt;/p&gt;&#xA;&lt;p&gt;If you are not seeing any nodes to the left of a particular node, move the pointer over the node to show one or two buttons at the top of the node.&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;Graph node buttons&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/GraphNodeButtons.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;Clicking the left button toggles showing and hiding the nodes to the left of the selected node. If no buttons appear, you reached the end of a path.&lt;/p&gt;&#xA;&lt;h2 id=&#34;do-you-want-to-learn-more-about-the-swiftui-instrument&#34;&gt;Do you want to learn more about the SwiftUI instrument?&lt;/h2&gt;&#xA;&lt;p&gt;I wrote a book, &lt;em&gt;Profiling Swift Apps&lt;/em&gt;, that shows you how to use Instruments to find and fix problems in your code. The book has a chapter on using the SwiftUI instrument to find problems in your SwiftUI code. You can learn more about the book and download a sample at the following link:&lt;/p&gt;&#xA;&lt;p&gt;&lt;a href=&#34;https://swiftdevjournal.com/instruments-book/&#34;&gt;Profiling Swift Apps page&lt;/a&gt;&lt;/p&gt;&#xA;</description>
    </item>
    <item>
      <title>Find the Slow Spots in Your Code with the CPU Profiler Instrument</title>
      <link>https://swiftdevjournal.com/posts/cpu-profiler/</link>
      <pubDate>Thu, 24 Jul 2025 13:29:07 -0400</pubDate>
      <guid>https://swiftdevjournal.com/posts/cpu-profiler/</guid>
      <description>&lt;p&gt;If you find your Swift app is running slowly, Instruments includes a CPU Profiler instrument to help you find the code causing your app to run slowly. This article shows you how to use the CPU Profiler instrument to find the slow code in your app.&lt;/p&gt;&#xA;&lt;p&gt;&lt;strong&gt;NOTE&lt;/strong&gt;&lt;/p&gt;&#xA;&lt;p&gt;Since I wrote this article, Apple made some changes to the CPU Profiler instrument. Instead of having Weight and Self Weight columns, there are Cyles and Self Cycles columns.&lt;/p&gt;&#xA;&lt;p&gt;You will have an easier time following this article if you choose the Time Profiler template instead of the CPU Profiler template.&lt;/p&gt;&#xA;&lt;h2 id=&#34;launching-instruments&#34;&gt;Launching Instruments&lt;/h2&gt;&#xA;&lt;p&gt;In Xcode choose Product &amp;gt; Profile or press Cmd-I to build your Xcode project and launch Instruments.&lt;/p&gt;&#xA;&lt;p&gt;When Instruments launches a window opens for you to choose a template to profile your app. Select the CPU Profiler template and click the Choose button. If you are running an older version of Xcode that does not have the CPU Profiler template, select the Time Profiler template.&lt;/p&gt;&#xA;&lt;h2 id=&#34;profiling-your-app&#34;&gt;Profiling Your App&lt;/h2&gt;&#xA;&lt;p&gt;Click the Record button at the top of the trace document window or press Cmd-R to start profiling your app. Run your app.&lt;/p&gt;&#xA;&lt;p&gt;Click the Pause button or press Cmd-Shift-R to pause recording. Click the Stop button or press Cmd-Dot to stop recording.&lt;/p&gt;&#xA;&lt;h2 id=&#34;reading-the-profiling-data&#34;&gt;Reading the Profiling Data&lt;/h2&gt;&#xA;&lt;p&gt;When you stop recording Instruments shows the call tree view.&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;CPU Profiler call tree view&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/CPUProfilerCallTreeView.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;The call tree view has a listing for each function that executed while profiling.&lt;/p&gt;&#xA;&lt;h3 id=&#34;finding-your-code-in-the-call-tree&#34;&gt;Finding Your Code in the Call Tree&lt;/h3&gt;&#xA;&lt;p&gt;When you first look at the call tree view, you will see it shows lots of functions that you didn&amp;rsquo;t write. How do you find your functions in the call tree view?&lt;/p&gt;&#xA;&lt;p&gt;To find your code in the call tree view, click the Call Tree button at the bottom of the window and click the Hide System Libraries and Invert Call Tree checkboxes.&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;CPU Profiler invert call tree&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/CPUProfilerInvertCallTree.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;Hiding the system library code makes it easier to find your app&amp;rsquo;s functions in the call tree view. Inverting the call tree brings the executed functions to the top of the call tree view.&lt;/p&gt;&#xA;&lt;h3 id=&#34;finding-the-slow-code&#34;&gt;Finding the Slow Code&lt;/h3&gt;&#xA;&lt;p&gt;How do you know which functions are the slow functions?&lt;/p&gt;&#xA;&lt;p&gt;Each function in the call tree view has a Weight value and a Self Weight value. The Weight value tells you how long the function was on the call stack. The Self Weight value tells you how long the function was at the top of the call stack.&lt;/p&gt;&#xA;&lt;p&gt;The Self Weight value is more important. Suppose you have a function A that calls functions X, Y, and Z. The Weight value for A tells you the amount of time your app was in functions A, X, Y, and Z. The Self Weight value for A tells you the amount of time your app was in A. When you&amp;rsquo;re looking for the slow spots in your code, look at functions with a high Self Weight value.&lt;/p&gt;&#xA;&lt;p&gt;Clicking the Self Weight column heading sorts the call tree view listings by their Self Weight value. Sorting by Self Weight brings the slow functions to the top of the call tree view.&lt;/p&gt;&#xA;&lt;h3 id=&#34;viewing-the-slow-code&#34;&gt;Viewing the Slow Code&lt;/h3&gt;&#xA;&lt;p&gt;Double-clicking a function in the call tree view opens the source view, where you can see the lines of code that take the most time in the function. Make sure you double-click a function you wrote. If you double-click a function you didn&amp;rsquo;t write, the source view shows unreadable assembly language code.&lt;/p&gt;&#xA;&lt;h2 id=&#34;do-you-want-to-learn-more-about-instruments&#34;&gt;Do you want to learn more about Instruments?&lt;/h2&gt;&#xA;&lt;p&gt;I wrote a book, &lt;em&gt;Profiling Swift Apps&lt;/em&gt;, that shows you how to use Instruments to find and fix problems in your code. The book will help you make apps that run faster and use less memory. You can learn more about the book and download a sample at the following link:&lt;/p&gt;&#xA;&lt;p&gt;&lt;a href=&#34;https://swiftdevjournal.com/instruments-book/&#34;&gt;Profiling Swift Apps page&lt;/a&gt;&lt;/p&gt;&#xA;</description>
    </item>
    <item>
      <title>Instruments Flame Graph Introduction</title>
      <link>https://swiftdevjournal.com/posts/instruments-flame-graph-intro/</link>
      <pubDate>Mon, 24 Mar 2025 14:09:38 -0400</pubDate>
      <guid>https://swiftdevjournal.com/posts/instruments-flame-graph-intro/</guid>
      <description>&lt;p&gt;Apple added flame graphs to Instruments in Xcode 16 to let developers visualize call tree statistics. Unfortunately Apple did not add much documentation on using flame graphs. I&amp;rsquo;m writing this article to partially fill the documentation void.&lt;/p&gt;&#xA;&lt;h2 id=&#34;showing-the-flame-graph&#34;&gt;Showing the Flame Graph&lt;/h2&gt;&#xA;&lt;p&gt;You must be in the call tree view to show the flame graph.&lt;/p&gt;&#xA;&lt;p&gt;There are two buttons on the right side above the detail view. Click the rightmost button to show the flame graph.&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;Flame Graph Button&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/FlameGraphButtonArrow.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;If you don&amp;rsquo;t see the buttons, the instrument does not show flame graphs. Currently only the Time Profiler instrument shows flame graphs. Some time in the future (hopefully soon) all the instruments that have a call tree view will show flame graphs.&lt;/p&gt;&#xA;&lt;h2 id=&#34;reading-the-flame-graph&#34;&gt;Reading the Flame Graph&lt;/h2&gt;&#xA;&lt;p&gt;When you click the button to show the flame graph, the flame graph initially looks similar to the following screenshot:&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;Flame Graph at Start&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/FlameGraphAtStart.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;The flame graph consists of stacks of rectangles. Each rectangle represents a function in your app’s call stack. Looking at the screenshot of the flame graph, you will notice that iOS and Mac apps have a lot of functions. Most of the rectangles are so narrow that you can&amp;rsquo;t read the function names.&lt;/p&gt;&#xA;&lt;p&gt;The top of the flame graph shows the function at the bottom of the call stack. This function is most likely the name of your app. Underneath the top rectangle are rectangles for the functions the bottom function called. The stack of rectangles continues downward until you reach the bottom rectangle, which is the function at the top of the call stack.&lt;/p&gt;&#xA;&lt;p&gt;One area where flame graphs excel is telling you the relative amount of time spent in the functions that a function calls. Suppose you have a function A that calls functions B, C, and D. You can tell whether your app spends more time in B, C, or D by the width of the rectangle. The wider the rectangle, the more time the function was on the call stack.&lt;/p&gt;&#xA;&lt;p&gt;If you look at the second row in the flame graph screenshot, you will see the &lt;code&gt;start&lt;/code&gt; function is on the call stack the most, over 70 percent of the time. The &lt;code&gt;start_wqthread&lt;/code&gt; function is on the call stack the second most, around 10 percent. After that are a bunch of other functions whose names you can&amp;rsquo;t read. The names of the functions and the percentages aren&amp;rsquo;t important in this case because they involve code I didn&amp;rsquo;t write. I&amp;rsquo;m using the second row as an example of reading the flame graph. You have to move farther down the flame graph to find code you wrote.&lt;/p&gt;&#xA;&lt;p&gt;The functions that spend the most time on the call stack appear on the left side of the graph.&lt;/p&gt;&#xA;&lt;h2 id=&#34;finding-your-code-in-the-flame-graph&#34;&gt;Finding Your Code in the Flame Graph&lt;/h2&gt;&#xA;&lt;p&gt;Functions you wrote have a blue rectangle. You must scroll down the flame graph to find your code because the top of the graph has blue rectangles for functions in your app that you didn&amp;rsquo;t write, such as &lt;code&gt;main&lt;/code&gt;.&lt;/p&gt;&#xA;&lt;p&gt;The easiest way to find your code is to hide functions in system libraries from the flame graph. Click the Call Tree button at the bottom of the window and select the Hide System Libraries checkbox.&lt;/p&gt;&#xA;&lt;h2 id=&#34;navigating-the-flame-graph&#34;&gt;Navigating the Flame Graph&lt;/h2&gt;&#xA;&lt;p&gt;Click a rectangle in the flame graph to select it. After selecting a rectangle, use the arrow keys to navigate the flame graph.&lt;/p&gt;&#xA;&lt;h2 id=&#34;zooming-the-flame-graph&#34;&gt;Zooming the Flame Graph&lt;/h2&gt;&#xA;&lt;p&gt;The number of functions in iOS and Mac apps makes it tough to read the function names for most of the flame graph rectangles. How do you zoom the flame graph so you can read those function names?&lt;/p&gt;&#xA;&lt;p&gt;Create a zoom area. Start by clicking in the flame graph to establish the start of the zoom area. Hold down the Option key, scroll, and release the mouse button to set the zoom area. You can also zoom with a trackpad gesture, but I don&amp;rsquo;t have a trackpad to test this.&lt;/p&gt;&#xA;&lt;p&gt;Combine creating a zoom area and hiding system libraries to make your function names readable in the flame graph.&lt;/p&gt;&#xA;&lt;p&gt;To zoom out, hold down the Option key and click in the graph. Scroll to the top of the flame graph and option-click to zoom out completely.&lt;/p&gt;&#xA;&lt;h2 id=&#34;summary&#34;&gt;Summary&lt;/h2&gt;&#xA;&lt;p&gt;The following list has the most important things to remember when reading Instruments flame graphs:&lt;/p&gt;&#xA;&lt;ul&gt;&#xA;&lt;li&gt;Rectangle width indicates the percentage of time the function was on the call stack.&lt;/li&gt;&#xA;&lt;li&gt;The functions that spend the most time on the call stack appear on the left side of the graph.&lt;/li&gt;&#xA;&lt;li&gt;Functions in your app have blue rectangles.&lt;/li&gt;&#xA;&lt;li&gt;Hide system libraries to focus on your code. Click the Call Tree button at the bottom of the window to hide system libraries.&lt;/li&gt;&#xA;&lt;li&gt;Option-scroll to zoom the flame graph to read function names.&lt;/li&gt;&#xA;&lt;/ul&gt;&#xA;&lt;h2 id=&#34;acknowledgments&#34;&gt;Acknowledgments&lt;/h2&gt;&#xA;&lt;p&gt;Thanks to James Dempsey and Philippe Casgrain for the information on zooming the flame graph.&lt;/p&gt;&#xA;&lt;h2 id=&#34;do-you-want-to-learn-more-about-instruments&#34;&gt;Do you want to learn more about Instruments?&lt;/h2&gt;&#xA;&lt;p&gt;I wrote a book, &lt;em&gt;Profiling Swift Apps&lt;/em&gt;, that shows you how to use Instruments to find and fix problems in your code. The book will help you make apps that run faster and use less memory. You can learn more about the book and download a sample at the following link:&lt;/p&gt;&#xA;&lt;p&gt;&lt;a href=&#34;https://swiftdevjournal.com/instruments-book/&#34;&gt;Profiling Swift Apps page&lt;/a&gt;&lt;/p&gt;&#xA;</description>
    </item>
    <item>
      <title>See How Many Times Your SwiftUI Views Redraw Using Instruments</title>
      <link>https://swiftdevjournal.com/posts/swiftui-instruments/</link>
      <pubDate>Mon, 10 Mar 2025 12:07:02 -0500</pubDate>
      <guid>https://swiftdevjournal.com/posts/swiftui-instruments/</guid>
      <description>&lt;p&gt;If you run into a performance problem in your SwiftUI app, the cause could be your app&amp;rsquo;s views redrawing too often. Apple provides instruments in the Instruments app that let you see how many times SwiftUI draws your app&amp;rsquo;s views and the view properties that trigger redraws. This article shows how to use those instruments.&lt;/p&gt;&#xA;&lt;h2 id=&#34;profile-your-app&#34;&gt;Profile Your App&lt;/h2&gt;&#xA;&lt;p&gt;Take the following steps to profile your app with the SwiftUI instruments:&lt;/p&gt;&#xA;&lt;ol&gt;&#xA;&lt;li&gt;Go to Xcode.&lt;/li&gt;&#xA;&lt;li&gt;Press Cmd-I or choose Product &amp;gt; Profile to build your project and launch Instruments.&lt;/li&gt;&#xA;&lt;li&gt;Choose SwiftUI from the template list.&lt;/li&gt;&#xA;&lt;li&gt;Click the Choose button.&lt;/li&gt;&#xA;&lt;li&gt;Click the Record button above the sidebar to start profiling.&lt;/li&gt;&#xA;&lt;li&gt;Click the Stop button when you are finished.&lt;/li&gt;&#xA;&lt;/ol&gt;&#xA;&lt;p&gt;The SwiftUI template has the following instruments:&lt;/p&gt;&#xA;&lt;ul&gt;&#xA;&lt;li&gt;View Body&lt;/li&gt;&#xA;&lt;li&gt;View Properties&lt;/li&gt;&#xA;&lt;li&gt;Core Animation Commits&lt;/li&gt;&#xA;&lt;li&gt;Time Profiler&lt;/li&gt;&#xA;&lt;li&gt;Hangs&lt;/li&gt;&#xA;&lt;/ul&gt;&#xA;&lt;p&gt;I cover the View Body and View Properties instruments in this article. Read the following article to learn more about the Time Profiler instrument:&lt;/p&gt;&#xA;&lt;p&gt;&lt;a href=&#34;https://swiftdevjournal.com/finding-the-slow-spots-in-your-code-with-the-time-profiler-instrument/&#34;&gt;Finding the Slow Spots in Your Code with the Time Profiler Instrument&lt;/a&gt;&lt;/p&gt;&#xA;&lt;h2 id=&#34;see-the-number-of-view-redraws&#34;&gt;See the Number of View Redraws&lt;/h2&gt;&#xA;&lt;p&gt;Use the View Body instrument to see statistics about the redraws of the SwiftUI views in your app. The View Body instrument table has the following columns of data:&lt;/p&gt;&#xA;&lt;ul&gt;&#xA;&lt;li&gt;Count&lt;/li&gt;&#xA;&lt;li&gt;Total Duration&lt;/li&gt;&#xA;&lt;li&gt;Minimum Duration&lt;/li&gt;&#xA;&lt;li&gt;Average Duration&lt;/li&gt;&#xA;&lt;li&gt;Maximum Duration&lt;/li&gt;&#xA;&lt;li&gt;Standard Deviation Duration&lt;/li&gt;&#xA;&lt;/ul&gt;&#xA;&lt;p&gt;The most important columns are Count, Total Duration, and Average Duration. The Count column tells you how many times SwiftUI drew the view. The Total Duration column tells you the total time of those draws. The Average Duration column tells you the average time of each draw.&lt;/p&gt;&#xA;&lt;p&gt;The View Body instrument table has at least two rows: one for SwiftUI and one for your app. Start by looking at the statistics for your app. You will see the total number of times SwiftUI drew your app&amp;rsquo;s views.&lt;/p&gt;&#xA;&lt;p&gt;To see what views were drawn the most, click the disclosure triangle next to your app. There will be a row for each view in your SwiftUI app.&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;App view stats&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/ViewBodyInstrumentAppViewsStats.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;The views that were drawn the most should appear at the top. If you don&amp;rsquo;t see the views that were drawn the most, click the Count table header to sort the views by count.&lt;/p&gt;&#xA;&lt;h1 id=&#34;see-the-properties-that-trigger-redraws&#34;&gt;See the Properties that Trigger Redraws&lt;/h1&gt;&#xA;&lt;p&gt;If you find one of your views is being redrawn often, you want to figure out what is causing the view to redraw so much. How do you find the cause of redraws?&lt;/p&gt;&#xA;&lt;p&gt;SwiftUI views redraw when the data bound to the views changes. Use the View Properties instrument to see the properties (variables) that change the most. Anything in your code that uses property wrappers like &lt;code&gt;@State&lt;/code&gt; and &lt;code&gt;@Binding&lt;/code&gt; will appear in this instrument.&lt;/p&gt;&#xA;&lt;p&gt;When you select the View Properties instrument, you will see a long list of properties with their current values. You can get more useful information from the summary. Press Cmd-2 or choose Summary from the jump bar to see the summary.&lt;/p&gt;&#xA;&lt;p&gt;The summary looks similar to the summary for the View Body instrument. There are rows for SwiftUI and your app. There is one column that tells you the number of updates.&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;View property app stats&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/ViewPropertyInstrumentAppStats.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;Where the View Properties instrument differs is it has levels you can drill down by clicking disclosure triangles. The View Properties instrument has the following levels:&lt;/p&gt;&#xA;&lt;ul&gt;&#xA;&lt;li&gt;View type&lt;/li&gt;&#xA;&lt;li&gt;Property type&lt;/li&gt;&#xA;&lt;li&gt;Property value&lt;/li&gt;&#xA;&lt;/ul&gt;&#xA;&lt;p&gt;The view types for your app are your app&amp;rsquo;s views. They should be the same as the views in the View Body instrument.&lt;/p&gt;&#xA;&lt;p&gt;The property types are the data types for the properties in your SwiftUI views. An example of a property type in a SwiftUI view is &lt;code&gt;Binding&amp;lt;String&amp;gt;&lt;/code&gt;, which is a binding to a string. The instrument shows the data types, not the names of your variables.&lt;/p&gt;&#xA;&lt;p&gt;The property values show the different values the property had during profiling. A Boolean property will show the number of times it was set to true and set to false.&lt;/p&gt;&#xA;&lt;p&gt;You are noticing there&amp;rsquo;s a lot of disclosure triangle clicking when looking at view properties. Option-clicking a disclosure triangle will expand the list to show all the levels so you don&amp;rsquo;t have to click as much. Option-clicking again will contract the list.&lt;/p&gt;&#xA;&lt;h2 id=&#34;do-you-want-to-learn-more-about-instruments&#34;&gt;Do you want to learn more about Instruments?&lt;/h2&gt;&#xA;&lt;p&gt;I wrote a book, &lt;em&gt;Profiling Swift Apps&lt;/em&gt;, that shows you how to use Instruments to find and fix problems in your code. The book will help you make apps that run faster and use less memory. You can learn more about the book and download a sample at the following link:&lt;/p&gt;&#xA;&lt;p&gt;&lt;a href=&#34;https://swiftdevjournal.com/instruments-book/&#34;&gt;Profiling Swift Apps page&lt;/a&gt;&lt;/p&gt;&#xA;</description>
    </item>
    <item>
      <title>Finding the Slow Spots in Your Code with the Time Profiler Instrument</title>
      <link>https://swiftdevjournal.com/finding-the-slow-spots-in-your-code-with-the-time-profiler-instrument/</link>
      <pubDate>Mon, 07 Jan 2019 19:55:55 +0000</pubDate>
      <guid>https://swiftdevjournal.com/finding-the-slow-spots-in-your-code-with-the-time-profiler-instrument/</guid>
      <description>&lt;p&gt;I continue my coverage of Instruments with the Time Profiler instrument. If your app is running slowly, use the Time Profiler instrument to find the slow spots in your code so you know where to optimize.&lt;/p&gt;&#xA;&lt;p&gt;If you are new to Instruments, I recommend reading the &lt;a href=&#34;https://swiftdevjournal.com/measuring-your-apps-memory-usage-with-instruments/&#34;&gt;Measuring Your App&amp;rsquo;s Memory Usage with Instruments article&lt;/a&gt;. That article provides an introduction to Instruments and covers some aspects of using Instruments this article glosses over.&lt;/p&gt;&#xA;&lt;h3 id=&#34;howthetimeprofilerinstrumentworks&#34;&gt;How the Time Profiler Instrument Works&lt;/h3&gt;&#xA;&lt;p&gt;The Time Profiler instrument records the call stack every millisecond. The function at the top of the call stack is the function your app is currently executing. If a function appears at the top of the call stack in a lot of samples, that&amp;rsquo;s a sign your app is spending a lot of time in that function.&lt;/p&gt;&#xA;&lt;h3 id=&#34;launchandrecord&#34;&gt;Launch and Record&lt;/h3&gt;&#xA;&lt;p&gt;Choose Product &amp;gt; Profile in Xcode to launch Instruments. Select the Time Profiler template and click the Choose button.&lt;/p&gt;&#xA;&lt;p&gt;Click the Record button to launch your app and start profiling.&lt;/p&gt;&#xA;&lt;h3 id=&#34;controllingthegraph&#34;&gt;Controlling the Graph&lt;/h3&gt;&#xA;&lt;p&gt;When you pause recording you&amp;rsquo;ll notice the Time Profiler instrument shows a lot of graphs. There&amp;rsquo;s a graph for each thread, and iOS and Mac apps have a surprisingly high number of threads.&lt;/p&gt;&#xA;&lt;p&gt;Above the graph is a series of buttons to control what graphs appear in the trace document window.&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;graph filter&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/GraphFilter.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;You can show instruments, threads, or CPU cores. You can also use the search field to filter what graphs appear. At the start you should focus on instruments, specifically CPU usage, because it helps find the slow spots in your code.&lt;/p&gt;&#xA;&lt;h3 id=&#34;cpuusagegraph&#34;&gt;CPU Usage Graph&lt;/h3&gt;&#xA;&lt;p&gt;Starting with Xcode 10 the Time Profiler instrument has two graphs: CPU usage and life cycle. If you move the mouse cursor over the CPU usage graph, tooltips appear with the percentage of CPU usage at that moment in the recording.&lt;/p&gt;&#xA;&lt;h3 id=&#34;lifecyclegraph&#34;&gt;Life Cycle Graph&lt;/h3&gt;&#xA;&lt;p&gt;The life cycle graph reports the current state of your app: initializing, launching, foreground, or background. If you move the mouse over the life cycle graph, tooltips tell you the state of the app and the amount of time the app was in that state.&lt;/p&gt;&#xA;&lt;p&gt;Older versions of Xcode do not have a life cycle graph.&lt;/p&gt;&#xA;&lt;h3 id=&#34;profiledata&#34;&gt;Profile Data&lt;/h3&gt;&#xA;&lt;p&gt;The Time Profiler instrument shows the call tree view initially. Click the Call Tree button at the bottom of the window and select the Invert Call Tree and Hide System Libraries checkboxes to make your code easier to find in the call tree view.&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;call tree&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/CallTreeTimeProfiler.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;For each function the call tree tells you its weight and it self weight. The weight is expressed as a time and a percentage. The weight measures the amount of time the function was on the call stack. The self weight measures the amount of time the function was at the top of the call stack.&lt;/p&gt;&#xA;&lt;p&gt;The Self Weight column is more important. Suppose you have a function A that calls functions B and C. The Weight column for A tells you the amount of time your app was in functions A, B, and C. The Self Weight column for A tells you the amount of time your app was in A. When you&amp;rsquo;re looking for the slow spots in your code, look at functions with a high self weight.&lt;/p&gt;&#xA;&lt;p&gt;Double-clicking a function opens the source view, where you can see the lines of code that take the most time in the function.&lt;/p&gt;&#xA;&lt;h3 id=&#34;narrative&#34;&gt;Narrative&lt;/h3&gt;&#xA;&lt;p&gt;The narrative section has a listing for each event in the Life Cycle graph. Each listing has the start time relative to the start of the recording and a description of what the app is doing.&lt;/p&gt;&#xA;&lt;p&gt;Older versions of Xcode do not have a narrative section.&lt;/p&gt;&#xA;&lt;h3 id=&#34;samples&#34;&gt;Samples&lt;/h3&gt;&#xA;&lt;p&gt;If you choose Samples from the jump bar, you can look at every sample the Time Profiler instrument took during the recording. Instruments shows the following data for each sample:&lt;/p&gt;&#xA;&lt;ul&gt;&#xA;&lt;li&gt;Sample time, relative to the start of recording&lt;/li&gt;&#xA;&lt;li&gt;Core, the CPU core&lt;/li&gt;&#xA;&lt;li&gt;Process, which is the name of your app&lt;/li&gt;&#xA;&lt;li&gt;Thread&lt;/li&gt;&#xA;&lt;li&gt;State, which is usually Running&lt;/li&gt;&#xA;&lt;li&gt;Backtrace, which lists the function at the top of the call stack&lt;/li&gt;&#xA;&lt;/ul&gt;&#xA;&lt;p&gt;The extended detail view shows a compressed backtrace. If you want to see every function in the call stack, click the button at the top right of the backtrace.&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;expanded backtrace&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/ExpandBacktraceHighlighted.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;Remember that the Time Profiler instrument takes a sample every millisecond so there are a lot of samples to go through.&lt;/p&gt;&#xA;&lt;h3 id=&#34;cpucores&#34;&gt;CPU Cores&lt;/h3&gt;&#xA;&lt;p&gt;If you move the mouse cursor over a CPU core in the graph, a tooltip appears showing you the percentage of CPU usage for that core at that moment in the recording.&lt;/p&gt;&#xA;&lt;p&gt;Selecting a CPU core from the instrument list fills the detail view with call tree statistics for that core. Choosing Samples from the jump bar shows all the samples Instruments recorded for that CPU core.&lt;/p&gt;&#xA;&lt;h3 id=&#34;threads&#34;&gt;Threads&lt;/h3&gt;&#xA;&lt;p&gt;If you move the mouse cursor over a thread in the graph, a tooltip appears showing the percentage of CPU usage for that thread at that moment in the recording. The graph can tell you if the main thread is doing too much work.&lt;/p&gt;&#xA;&lt;p&gt;Selecting a thread from the instrument list fills the detail view with call tree statistics for that thread. Choosing Samples from the jump bar shows all the samples Instruments recorded for that thread.&lt;/p&gt;&#xA;&lt;h3 id=&#34;summary&#34;&gt;Summary&lt;/h3&gt;&#xA;&lt;p&gt;The main point of using the Time Profiler instrument is to find the slow spots in your code. Look for functions in the call tree with a high self weight. If you need to make your app run faster, start by optimizing those functions with a high self weight.&lt;/p&gt;&#xA;&lt;h2 id=&#34;do-you-want-to-learn-more-about-instruments&#34;&gt;Do you want to learn more about Instruments?&lt;/h2&gt;&#xA;&lt;p&gt;I wrote a book, &lt;em&gt;Profiling Swift Apps&lt;/em&gt;, that shows you how to use Instruments to find and fix problems in your code. The book will help you make apps that run faster and use less memory. You can learn more about the book and download a sample at the following link:&lt;/p&gt;&#xA;&lt;p&gt;&lt;a href=&#34;https://swiftdevjournal.com/instruments-book/&#34;&gt;Profiling Swift Apps page&lt;/a&gt;&lt;/p&gt;&#xA;</description>
    </item>
    <item>
      <title>Measuring Your App’s Memory Usage with Instruments</title>
      <link>https://swiftdevjournal.com/measuring-your-apps-memory-usage-with-instruments/</link>
      <pubDate>Fri, 14 Dec 2018 05:11:05 +0000</pubDate>
      <guid>https://swiftdevjournal.com/measuring-your-apps-memory-usage-with-instruments/</guid>
      <description>&lt;p&gt;On Stack Overflow I see many questions from people who have trouble interpreting the data Instruments generates. After reading this article you&amp;rsquo;ll know how to interpret the data Instruments generates for the Allocations and Leaks instruments and learn tips you can use with other instruments.&lt;/p&gt;&#xA;&lt;h3 id=&#34;whatisinstruments&#34;&gt;What is Instruments?&lt;/h3&gt;&#xA;&lt;p&gt;Instruments is an app that is bundled with Xcode to record and display statistics about your app as it runs. Instruments comes with a collection of instruments, each of which records a specific set of statistics. Some popular instruments include the following:&lt;/p&gt;&#xA;&lt;ul&gt;&#xA;&lt;li&gt;The Leaks instrument checks your app for memory leaks.&lt;/li&gt;&#xA;&lt;li&gt;The Allocations instrument records statistics about memory allocations.&lt;/li&gt;&#xA;&lt;li&gt;The Time Profiler instrument measures CPU usage and helps you find the slow spots in your code.&lt;/li&gt;&#xA;&lt;/ul&gt;&#xA;&lt;p&gt;If you&amp;rsquo;re learning iOS or Mac development, you&amp;rsquo;re not going to use Instruments at first. You normally use Instruments when you get closer to shipping an app. But if your iOS app is generating memory warnings when you run it or your app runs really slow, you&amp;rsquo;ll want to profile the app with Instruments.&lt;/p&gt;&#xA;&lt;h3 id=&#34;launchinginstruments&#34;&gt;Launching Instruments&lt;/h3&gt;&#xA;&lt;p&gt;Because Instruments is located inside Xcode&amp;rsquo;s app bundle, you won&amp;rsquo;t be able to find it in the Finder. The easiest way to launch Instruments is to profile your project by choosing Product &amp;gt; Profile in Xcode. When Instruments launches, you will be asked to choose a template.&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;choose Instruments template&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/ChooseTemplateHighlighted.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;Select the Leaks template and click the Choose button. The Leaks template include both the Leaks and Allocations instruments.&lt;/p&gt;&#xA;&lt;h3 id=&#34;thetracedocumentwindow&#34;&gt;The Trace Document Window&lt;/h3&gt;&#xA;&lt;p&gt;When you click the Choose button, an empty trace document window opens in Instruments.&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;trace document window&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/TraceDocumentWindowHighlighted.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;Running from top to bottom, the main areas of the trace document window are the following:&lt;/p&gt;&#xA;&lt;ul&gt;&#xA;&lt;li&gt;Toolbar&lt;/li&gt;&#xA;&lt;li&gt;Instrument list&lt;/li&gt;&#xA;&lt;li&gt;Jump bar&lt;/li&gt;&#xA;&lt;li&gt;Detail view&lt;/li&gt;&#xA;&lt;li&gt;Extended detail view&lt;/li&gt;&#xA;&lt;li&gt;Bottom bar&lt;/li&gt;&#xA;&lt;/ul&gt;&#xA;&lt;p&gt;For this article the only toolbar items you need to worry about are the buttons to start/stop recording and pause recording on the left side of the toolbar. The toolbar also has controls to choose an app to profile, add an instrument to the trace, and show/hide different parts of the trace document window.&lt;/p&gt;&#xA;&lt;p&gt;The instrument list shows the instruments being used in the trace along with a graph for each instrument. The graph is going to be empty until you start recording.&lt;/p&gt;&#xA;&lt;p&gt;The jump bar allows you to choose what to show in the detail view. The detail view shows the profiling statistics. The extended detail view shows additional statistics. For most instruments the extended detail view shows the call stack.&lt;/p&gt;&#xA;&lt;p&gt;The bottom bar contains controls to filter the information that appears in the detail view.&lt;/p&gt;&#xA;&lt;h3 id=&#34;configuringaninstrumentoptional&#34;&gt;Configuring an Instrument (Optional)&lt;/h3&gt;&#xA;&lt;p&gt;You won&amp;rsquo;t need to configure any instruments to follow along with this tutorial. But when you use Instruments, you may need to configure an instrument, and it helps to configure the instrument before you start recording.&lt;/p&gt;&#xA;&lt;p&gt;Choose File &amp;gt; Recording Options to configure an instrument. The following screenshot shows the configuration options for the Allocations instrument:&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;trace recording options&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/RecordingOptionsHighlighted.png&#34;&gt;&lt;/p&gt;&#xA;&lt;h3 id=&#34;profilingyourapp&#34;&gt;Profiling Your App&lt;/h3&gt;&#xA;&lt;p&gt;At this point you can start profiling your app. Click the Record button on the left side of the toolbar. Your app will launch. Use your app. When you are finished, you can either click the Pause button or the Stop button. The Leaks instrument is set to check for leaks every 10 seconds so you should run your app for at least 10 seconds.&lt;/p&gt;&#xA;&lt;p&gt;If you want to save your trace so you can look at the results later, choose File &amp;gt; Save.&lt;/p&gt;&#xA;&lt;h3 id=&#34;readingtheprofilingdata&#34;&gt;Reading the Profiling Data&lt;/h3&gt;&#xA;&lt;p&gt;Now comes the hard part: making sense of all the data that Instruments generates. Let&amp;rsquo;s start with the graph. If you move the mouse cursor inside the graph, Instruments shows a tooltip with a piece of data about the graph. The following image shows the memory usage for the Allocations instrument:&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;memory tool tip&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/MemoryToolTip.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;You can focus on a specific time interval in the graph by setting an inspection range. Click inside an instrument&amp;rsquo;s graph and drag to create the inspection range. The inspection range is shaded blue, which you can see in the following screenshot:&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;partial graph time period&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/PartialGraphTimePeriod.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;When you set an inspection range, the statistics in the detail view change to reflect the time interval in the inspection range. Clicking in the graph outside of the inspection range you set clears the inspection range.&lt;/p&gt;&#xA;&lt;h3 id=&#34;allocationsinstrumentresults&#34;&gt;Allocations Instrument Results&lt;/h3&gt;&#xA;&lt;p&gt;Now it&amp;rsquo;s time to look at data for specific instruments. Let&amp;rsquo;s start with the Allocations instrument. If you select the Allocations instrument from the instrument list, the detail view shows a summary of the memory allocation data. The most important data is at the top.&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;memory usage stats&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/MemoryUsage.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;To determine how much memory your app is currently using, look at the Persistent Bytes column for the category All Heap Allocations. The text is a little small in the screenshot, but it says the app is using 9.64 MB of memory, which is good for an iOS or Mac app. The Allocations instrument does not record OpenGL/ES or Metal texture memory. If your app allocates texture memory, your actual memory use will be higher than what Instruments reports. You may also want to click the checkbox in the Graph column to show the heap allocation totals in the graph.&lt;/p&gt;&#xA;&lt;p&gt;The Allocations instrument has the following columns of data for each memory category:&lt;/p&gt;&#xA;&lt;ul&gt;&#xA;&lt;li&gt;Persistent Bytes, which is the amount of allocated memory that hasn&amp;rsquo;t been freed yet.&lt;/li&gt;&#xA;&lt;li&gt;# Persistent, which is the number of memory allocations that haven&amp;rsquo;t been freed yet.&lt;/li&gt;&#xA;&lt;li&gt;# Transient, which is the total number of memory allocations that have been freed.&lt;/li&gt;&#xA;&lt;li&gt;Total Bytes, which is the total amount of allocated memory, including freed memory.&lt;/li&gt;&#xA;&lt;li&gt;# Total, which is the total number of memory allocations, including freed memory. The # Total column should equal the sum of the # Persistent and # Transient columns.&lt;/li&gt;&#xA;&lt;/ul&gt;&#xA;&lt;p&gt;Suppose your app makes 20 memory allocations of 1,000 bytes and frees the memory for 15 of the allocations. The Allocations instrument would report the following information:&lt;/p&gt;&#xA;&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;Persistent Bytes: 5,000&#xA;# Persistent: 5&#xA;# Transient: 15&#xA;Total Bytes: 20,000&#xA;# Total: 20&#xA;&lt;/code&gt;&lt;/pre&gt;&lt;h3 id=&#34;allocationsinstrumentcalltree&#34;&gt;Allocations Instrument Call Tree&lt;/h3&gt;&#xA;&lt;p&gt;If your app allocates a high amount of memory, the first thing you&amp;rsquo;ll want to know is where your code is making the big memory allocations. To find where you&amp;rsquo;re allocating memory, switch to the call tree view. In the jump bar, click on Statistics and choose Call Trees to switch to the call tree view.&lt;/p&gt;&#xA;&lt;p&gt;When you switch to the call tree view, you should configure Instruments to make finding your code easier in the call tree view. Click the Call Tree button in the bottom bar to open a popover with a series of checkboxes.&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;invert call tree&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/InvertCallTree.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;Select the Invert Call Tree and Hide System Libraries checkboxes. Inverting the call tree brings the memory allocating functions to the top. Hiding the system libraries hides Apple&amp;rsquo;s code, leaving your code in the call tree view.&lt;/p&gt;&#xA;&lt;p&gt;After selecting the checkboxes, the call tree view should show your code.&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;call tree&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/CallTree.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;Option-clicking a disclosure triangle next to a function in the call tree view expands its subtree so you don&amp;rsquo;t have to be constantly clicking disclosure triangles. Option-clicking again on the expanded disclosure triangle contracts the subtree.&lt;/p&gt;&#xA;&lt;p&gt;For each function in the call tree, the Allocations instrument shows the bytes used and the allocation count. The bytes used is represented both as an amount and a percentage of the total memory allocated. Here&amp;rsquo;s the listing from the &lt;code&gt;Framesetter.init&lt;/code&gt; listing:&lt;/p&gt;&#xA;&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;308.86 KB   1.2%    42&#xA;&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;The line says the &lt;code&gt;Framesetter.init&lt;/code&gt; function and any functions in its subtree allocated 308.86 KB of memory, which is 1.2% percent of the total allocated memory. This function and any functions in its subtree made 42 allocations.&lt;/p&gt;&#xA;&lt;p&gt;The subtrees keep Instruments from telling you the exact amount of memory each function allocates. Inverting the call tree reduces the subtree, which makes the listing for a function in an inverted call tree the closest approximation to the amount of memory that function is allocating. If you set an inspection range in the graph, the listing reflects the amount of memory allocated in the inspection range&amp;rsquo;s time interval.&lt;/p&gt;&#xA;&lt;h4 id=&#34;mainlisting&#34;&gt;main Listing&lt;/h4&gt;&#xA;&lt;p&gt;For most Mac and iOS apps, the first listing in the call tree view is the &lt;code&gt;main&lt;/code&gt; function. This function is going to have a high amount of bytes used and allocations. If you don&amp;rsquo;t invert the call tree, the &lt;code&gt;main&lt;/code&gt; function will show 100% bytes used. That&amp;rsquo;s because &lt;code&gt;main&lt;/code&gt; is the starting point of your app. Every function in your app will have &lt;code&gt;main&lt;/code&gt; in its call stack so every memory allocation your app makes will have &lt;code&gt;main&lt;/code&gt; in its call stack.&lt;/p&gt;&#xA;&lt;p&gt;When trying to figure out where your app allocates memory, don&amp;rsquo;t worry about the &lt;code&gt;main&lt;/code&gt; listing. The &lt;code&gt;main&lt;/code&gt; function doesn&amp;rsquo;t do much in most Mac and iOS apps. There isn&amp;rsquo;t much you can do in the &lt;code&gt;main&lt;/code&gt; function to reduce your app&amp;rsquo;s memory usage.&lt;/p&gt;&#xA;&lt;h4 id=&#34;sourceview&#34;&gt;Source View&lt;/h4&gt;&#xA;&lt;p&gt;Double-clicking a function in the call tree view shows the source view. For the Allocations instrument, the source view shows you the lines of code that allocated the memory along with the percentage of memory allocated. The percentage is relative to the function. If a line of code says 80%, it means that line of code allocated 80% of the memory the function allocated.&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;source view&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/SourceCodeView.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;Notice how each listing in the source view has an icon with an exclamation point. Clicking that icon shows the heaviest call stack for that line of code.&lt;/p&gt;&#xA;&lt;h3 id=&#34;leaksinstrumentresults&#34;&gt;Leaks Instrument Results&lt;/h3&gt;&#xA;&lt;p&gt;Now it&amp;rsquo;s time to look at the Leaks instrument. The graph will tell you if you have any memory leaks in your app. A memory leak occurs when your app allocates memory and never frees the memory. The following screenshot shows an example of the graph for the Leaks instrument:&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;leaks graph&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/LeaksGraph.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;The screenshot shows six memory leak checks. For the first four checks, Leaks found no memory leaks so it leaves a green icon with a checkmark on the graph. On the fifth check, Leaks found some leaks so it leaves a red icon with an X on the graph. On the last check Leaks found no new leaks so it leaves a gray icon with a dash on the graph.&lt;/p&gt;&#xA;&lt;h3 id=&#34;leaksinstrumentcalltree&#34;&gt;Leaks Instrument Call Tree&lt;/h3&gt;&#xA;&lt;p&gt;If Instruments finds memory leaks in your app, the next step is to find where the leaks are occurring in your code. The steps to do this are the same as for the Allocations instrument: switch to the call tree view by using the jump bar and select the Invert Call Tree and Hide System Libraries checkboxes from the Call Tree popover in the bottom bar. Selecting the checkboxes will limit the call tree listing to functions you wrote.&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;leaks call tree&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/LeaksCallTree.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;For each function in the call tree listing, Instruments shows the bytes used and the number of leaks. Like the Allocations instrument, the bytes used is represented both as an amount and a percentage, but in the Leaks instrument the percentage represents the percentage of total leaked memory. Here&amp;rsquo;s the listing for the &lt;code&gt;malloc&lt;/code&gt; function in the screenshot.&lt;/p&gt;&#xA;&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;19.12 KB    98.0%   92&#xA;&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;The listing says the &lt;code&gt;malloc&lt;/code&gt; function has 92 memory leaks totaling 19.12 KB. The leaks totaled 98% of the leaked memory in the app.&lt;/p&gt;&#xA;&lt;p&gt;Double-click any functions in your call tree view to see where the leaked memory is allocated.&lt;/p&gt;&#xA;&lt;p&gt;The fact that a function allocates leaked memory doesn&amp;rsquo;t necessarily mean the function is responsible for leaking the memory. But it&amp;rsquo;s a good place to start looking for the source of the leak.&lt;/p&gt;&#xA;&lt;h3 id=&#34;troubleshooting&#34;&gt;Troubleshooting&lt;/h3&gt;&#xA;&lt;p&gt;This section contains fixes for common issues people run into with Instruments.&lt;/p&gt;&#xA;&lt;h4 id=&#34;thecalltreeviewshowsmemoryaddresses&#34;&gt;The Call Tree View Shows Memory Addresses&lt;/h4&gt;&#xA;&lt;p&gt;A problem many people run into when using Instruments is the call tree view shows memory addresses instead of the names of functions. The usual cause of this problem is Instruments being unable to locate the dSYM file that contains the project&amp;rsquo;s debugging symbols. The function names are in the debugging symbols.&lt;/p&gt;&#xA;&lt;p&gt;To locate the dSYM file, choose File &amp;gt; Symbols in Instruments. A sheet like the following will open:&lt;/p&gt;&#xA;&lt;p&gt;&lt;img alt=&#34;locate dSYM file&#34; loading=&#34;lazy&#34; src=&#34;https://swiftdevjournal.com/images/LocatedSYMHighlighted.png&#34;&gt;&lt;/p&gt;&#xA;&lt;p&gt;Select your app from the left side of the sheet. Click the Locate button to find the dSYM file.&lt;/p&gt;&#xA;&lt;p&gt;The dSYM file is usually located in the same directory as the app bundle of the release version of your project. The app bundle is in the Derived Data folder. You can check the location of your Derived Data folder in Xcode by choosing File &amp;gt; Project Settings, but the Derived Data folder is usually in the following folder:&lt;/p&gt;&#xA;&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;/Users/YourUsername/Library/Developer/Xcode/DerivedData&#xA;&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;There will be a folder for your project in the Derived Data folder with a long string of random characters after the project name. The release version of the project is in the following folder:&lt;/p&gt;&#xA;&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;.../DerivedData/ProjectName/Build/Products/Release&#xA;&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;An iOS project will have the name &lt;code&gt;Release-iphoneos&lt;/code&gt; instead of &lt;code&gt;Release&lt;/code&gt;.&lt;/p&gt;&#xA;&lt;h4 id=&#34;thesourceviewdoesntshowsourcecode&#34;&gt;The Source View Doesn&amp;rsquo;t Show Source Code&lt;/h4&gt;&#xA;&lt;p&gt;You double-click a function in the call tree view, expecting to see that function&amp;rsquo;s code in the source view. But instead you see either assembly language code or a blank view that says Unavailable.&lt;/p&gt;&#xA;&lt;p&gt;The usual cause of this issue is double-clicking a function you didn&amp;rsquo;t write. Examples of functions you didn&amp;rsquo;t write include functions from Apple&amp;rsquo;s frameworks and default initializers in your structs and classes. Make sure you double-click a function you wrote.&lt;/p&gt;&#xA;&lt;h3 id=&#34;summary&#34;&gt;Summary&lt;/h3&gt;&#xA;&lt;p&gt;I want to summarize the most important points to take away from this article. These points apply to most instruments, not just the Leaks and Allocations instruments.&lt;/p&gt;&#xA;&lt;ul&gt;&#xA;&lt;li&gt;Choose Product &amp;gt; Profile in Xcode to profile your app.&lt;/li&gt;&#xA;&lt;li&gt;Use the call tree view to find problem areas in your code.&lt;/li&gt;&#xA;&lt;li&gt;Select the Invert Call Tree and Hide System Libraries checkboxes to find your code in the call tree view.&lt;/li&gt;&#xA;&lt;li&gt;Option-click the disclosure triangles in the call tree view to minimize the amount of clicking you have to do.&lt;/li&gt;&#xA;&lt;li&gt;Double-click a function in the call tree view to see statistics on specific lines of code.&lt;/li&gt;&#xA;&lt;li&gt;Don&amp;rsquo;t worry about the listing for the &lt;code&gt;main&lt;/code&gt; function in the call tree view. You have no control over &lt;code&gt;main&lt;/code&gt;.&lt;/li&gt;&#xA;&lt;/ul&gt;&#xA;&lt;h2 id=&#34;do-you-want-to-learn-more-about-instruments&#34;&gt;Do you want to learn more about Instruments?&lt;/h2&gt;&#xA;&lt;p&gt;I wrote a book, &lt;em&gt;Profiling Swift Apps&lt;/em&gt;, that shows you how to use Instruments to find and fix problems in your code. The book will help you make apps that run faster and use less memory. You can learn more about the book and download a sample at the following link:&lt;/p&gt;&#xA;&lt;p&gt;&lt;a href=&#34;https://swiftdevjournal.com/instruments-book/&#34;&gt;Profiling Swift Apps page&lt;/a&gt;&lt;/p&gt;&#xA;</description>
    </item>
  </channel>
</rss>
