Tue, 20 Sep 2005
As a sidenote, this reminds me a little of how LabView handled subfunction definitions: subfunctions are defined using the same visual tools as top-level functions. It worked, but 'felt' a little heavy weight in actual use.
reddit this! Digg Me!
The first time the macro MaybeToggleMAR is invoked, it displays the current state in the status bar, and sets a timer to expire in 3 seconds. If the macro is invoked a second time before the timer expires (easy to do if it's bound to a keystroke) the state is toggled. Technically speaking, the trickiest bit is that the function that sets the 3 second timer also has to handle cancelling any previous instance of the same timer. It works without the timer cancellation, but without it, the UI behaves oddly after multiple keypresses in rapid succession.
Chip Pearson's website has useful content discussing the Excel API's for Timers and the Status Bar.
Here's the code: to use it, stick it in a module and bind MaybeToggleMAR to the keyboard shortcut of your choice.
Option Explicit
Private MARChangesEnabled As Boolean
Public NextDisableTime As Double
Sub DisableMARChanges()
Application.StatusBar = False
MARChangesEnabled = False
End Sub
Sub DisableMARChangesSoon()
On Error Resume Next
Application.OnTime NextDisableTime, "DisableMARChanges", , False
NextDisableTime = Now + TimeSerial(0, 0, 3)
Application.OnTime NextDisableTime, "DisableMARChanges", , True
End Sub
Sub MaybeToggleMAR()
Dim NewStatusText As String
NewStatusText = ""
If MARChangesEnabled Then
Application.MoveAfterReturn = Not Application.MoveAfterReturn
NewStatusText = "Status changed: "
Else
MARChangesEnabled = True
NewStatusText = "Second press will change status: "
End If
If Application.MoveAfterReturn Then
NewStatusText = NewStatusText & "MoveAfterReturn Enabled"
Else
NewStatusText = NewStatusText & "MoveAfterReturn Disabled"
End If
Application.StatusBar = NewStatusText
DisableMARChangesSoon
End Sub
reddit this! Digg Me!
Wed, 07 Sep 2005
- The more use this kind of scaffolding code gets, it gets progressively more cost effective to write. Time spent before dumpers are in place reduces the amount of use they can get and makes them progressively less cost effective. Implement them early, if you can.
- Look for cheap alternatives already in your toolkit: Lisp can already print most of its structures, and .Net includes object serialization to XML. The standard solution might not be perfect, but it is 'free'.
- Make sure your dumpers are correct from the outset. The whole point of this is to save debugging time later on, if you can't trust your view into your data structures during debugging, it will cost you time.
- Dump into standard formats. If you can, dump into something like CSV, XML, S-expressions, or Dotty. If you have a considerable amount of data to analyze, this'll make it easier to use other tools to do some of the work.
- Maintain your dumpers. Your software isn't going to go away, and neither are your data structures. If it's useful during initial development, it's likely to be useful during maintenance.
- For structures that might be shared, or exist on the system heap, printing object addresses and reference counts can be very useful.
- For big structures, it can be useful to elide specific content. For example: a list of 1000 items can be printed as (item_0, item_1, item_2, ..., item_999 ).
- This stuff works for disk files too. For binary save formats, specific tooling to examine files can save time compared to an on-disk hex-editor/viewer. (Since you have code to read your disk format into a data structure in memory, if you also have code to dump your in-memory structure, this does not have to be much more work. Sharing code between the dump utility and the actual application also makes it more likely the dumper will show you the same view your application will see.)
- Reading dumped structures back in can also be useful.
reddit this! Digg Me!
[/tech/programming] permanent link
That leads me to a couple books I've been reading lately. The first is Lisp in Small Pieces, by Christian Queinnec. I'm only a couple chapters in (stuck on continuations right now), but it's already been pretty profound. So far, the aspect of the book that's been the most useful is that it has gone through several core design choices Lisp implementors have to make ( Lisp-1 vs. Lisp-2, Lexical Scope vs. Dynamic Scope, types of continuations to support), and goes into depth regarding the implications and history of the choices involved. I think I'm finally starting to understand more of the significance of funcall and function in Common Lisp, not to mention throw/catch and block/return-from.
Book two is The
First Computers--History and Architectures, edited by
Raul Rojas. This book is a collection
of papers discussing the architecture of significant early computers from the late
30's and 40's. The thing that's so unique about the book is that it focuses on
the architectural issues surrounding these machines: the kinds of hardware they
were built with, how they processed information, and how they were programmed. Just
as an example, it has a detailed description of many of ENIAC's functional units,
even going into descriptions of how problems were set up on the machine. Another
highlight of the book for me (so far) has been a description of Konrad Zuse's
relay-based Z3, down to the level of a system architectural diagram, schematics of
a few key circuits, and coverage of its microprogramming (!).
reddit this! Digg Me!