Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

What is the difference between finish and continue in browser()?

Tags:

r

debugging

In the help file for browser, there are two options that seem very similar:

f

finish execution of the current loop or function

c

exit the browser and continue execution at the next statement.

What is the difference between them and in what situations is the difference apparent?

Some clues about what may be the difference - I wrote a script called browse.R with the following contents:

for (i in 1:2){
  browser()
  print(i)
}

This is the results of usingc vs f:

> source("browse.R")
Called from: eval(expr, envir, enclos)
Browse[1]> c
[1] 1
Called from: eval(expr, envir, enclos)
Browse[1]> c
[1] 2
> source("browse.R")
Called from: eval(expr, envir, enclos)
Browse[1]> f
[1] 1
Browse[2]> f
[1] 2

Note that the level of Browse[n] changes. This still doesn't highlight any practical difference between them.

I also tried to see if perhaps things would disappear from the browser environment:

for (i in 1:2){
  a <- "not modified"
  browser()
  print(a)
}

Called from: top level 
Browse[1]> a <- "modified"
Browse[1]> f
[1] "modified"
Browse[1]> a
[1] "not modified"
Browse[1]> a <- "modified"
Browse[1]> c
[1] "modified"

So there's no difference there either.

like image 643
sebastian-c Avatar asked Apr 28 '16 12:04

sebastian-c


People also ask

When does the finish timer stop after page load?

For a web page that makes no requests after the page finishes loading, the Finish timer should stop shortly after the load timer. But for a web page that makes AJAX requests, the Finish timer will continue to run as the page continues to make requests after page load.

What is the finish time in Chrome DevTools?

The Finish time in Chrome Devtools includes the asynchronously loading (non blocking) objects/elements on the page which may continue downloading way after the onLoad event for the page has fired.

What is the finish timer and how does it work?

The Finish timer, in contrast, measures the amount of time between when the page started loading and when the browser finished making its last request. It's a little more complicated than that but that's the general gist.

Is finish time a good measure of web page response time?

The Finish time, although technically also a response time, doesn't have as much end-user implication. In some cases, it seems that the Finish timer never stops but continues increasing, so it may not be the best assessment of web page response time. Show activity on this post.


Video Answer


2 Answers

There is a small difference.

  • c immediately exits the browser (and debug mode) and after that executes the rest of the code in the normal way.
  • f on the contrary stays in the browser (and debug mode) while executing the rest of the function/loop. After the function/loop is finished, he also returns to the normal execution mode.

Source: R-source (line 1105-1117) and R-help

This has a few implications:

  • c closes the browser. This means that a new browser call is called from a function. Therefore you will see the line: Called from: function(). f on the other hand will not close the browser and therefore you will not see this line. The source code for this behavior is here: https://github.com/wch/r-source/....
  • Because f stays in the browser, f also keeps track of the contextlevel:

The browser prompt is of the form Browse[n]>: here var{n} indicates the ‘browser level’. The browser can be called when browsing (and often is when debug is in use), and each recursive call increases the number. (The actual number is the number of ‘contexts’ on the context stack: this is usually 2 for the outer level of browsing and 1 when examining dumps in debugger)

These differences can be tested with the code:

> test <- function(){
      browser()
      browser()
  }

> test()
Called from: test()
Browse[1]> c
Called from: test()
Browse[1]> c

> test()
Called from: test()
Browse[1]> f
Browse[2]> f

As far as I see it, there is no practical difference between the two, unless there lies a practical purpose in the context stack. The debugging mode has no added value. The debug flag only opens the browser when you enter the function but since you are already inside the function, it will not trigger another effect.

like image 110
takje Avatar answered Oct 06 '22 19:10

takje


Difference Between Browser and Continue

At least for me, I feel the answer can be mapped out as a table, however, let's first frame up the usage of browser(), for those who may not yet have encountered it.

The browser function is the basis for the majority of R debugging techniques. Essentially, a call to browser halts execution and starts a special interactive session where you can inspect the current state of the computations and step through the code one command at a time.

Once in the browser, you can execute any R command. For example, one might view the local environment by using ls(); or choose to set new variables, or change the values assigned to variables simply by using the standard methods for assigning values to variables. The browser also understands a small set of commands specific to it. Which leads us to a discussion on Finish and continue...

The subtlety in relation to Finish and continue is that:

  • Finish, or f: finishes execution of the current loop or function.
  • Continue, c: leaves interactive debugging and continues regular execution of the function. This is useful if you’ve fixed the bad state and want to check that the function proceeds correctly.

essentially, we talking about a subtlety in mode.

enter image description here

Browser / Recover Overview

At least for me, you have to view this in the context of debugging a program written in R. Specifically, how you might apply Finish and continue. I am sure many understand this, but I include for completeness as I personally really didn't for a long time.

  • browser allows you to look at the objects in the function in which the browser call is placed.
  • recover allows you to look at those objects as well as the objects in the caller of that function and all other active functions.

Liberal use of browser, recover, cat and print while you are writing functions allows your expectations and R's expectations to converge.

A very handy way of doing this is with trace. For example, if browsing at the end of the myFun function is convenient, then you can do:

trace(myFun, exit=quote(browser()))

You can customize the tracing with a command like:

trace(myFun, edit=TRUE)

If you run into an error, then debugging is the appropriate action. There are at least two approaches to debugging. The first approach is to look at the state of play at the point where the error occurs. Prepare for this by setting the error option. The two most likely choices are:

options(error=recover)

or

options(error=dump.frames)

The difference is that with recover you are automatically thrown into debug mode, but with dump.frames you start debugging by executing:

debugger()

In either case you are presented with a selection of the frames (environments) of active functions to inspect.

You can force R to treat warnings as errors with the command:

options(warn=2)

If you want to set the error option in your .First function, then you need a trick since not everything is in place at the time that .First is executed:

options(error=expression(recover()))

or

options(error=expression(dump.frames()))

The second idea for debugging is to step through a function as it executes. If you want to step through function myfun, then do:

debug(myfun)

and then execute a statement involving myfun. When you are done debugging, do:

undebug(myfun)

A more sophisticated version of this sort of debugging may be found in the debug package.

References:

  • R Inferno
    • http://www.burns-stat.com/pages/Tutor/R_inferno.pdf (Great Reference)
    • Circle 8 - Believing It Does as Intended (Page 45).
    • Author: Patrick Burns
  • R Programming for Bioinformatics
    • Author: Robert Gentleman
like image 3
Technophobe01 Avatar answered Oct 06 '22 21:10

Technophobe01