zoukankan      html  css  js  c++  java
  • visual studio 2005,visual studio 2008调出即时窗口

    在调试时,即时窗口(Immediate Window)非常有用。

    在调试时,调出即时窗口

    visual studio 2005 :Ctrl+Alt+I 或则 Ctr+D,I

    visual studio 2008 :  Ctrl+Alt+I

    visual studio 2003 :  Ctrl+Alt+I

     假设你正在会议室里演示即时编译的程序。有什么最佳的方式来进行演示呢?

    你还在往代码窗口里输入代码?这样,你得依赖听众的想像力 ―― 他们在脑海中构造这个程序是怎样运行的。此外,你还得依赖他们相信你的代码真的像和你所说的一样运作。
          或者你要不停的运行你的代码,这样程序的输出窗口会弹出,然后听众可以看到代码的实际工作情况?这是有风险的,因为每次切换代码和输出窗口会中断流程。并且你得依赖听众会记得他们每次看到的输出信息所对应的代码。
    我想这是一个可以被技术所解决的问题!我为Visual Studio 2008 写了一个小插件。它关注的是当前文本缓冲中所包含的代码,并在后台编译它,然后在前端窗口中显示输出。这一系列动作大概每2秒钟重复一次。你甚至不需要保 存再重新编译代码就能看到输出 了。这个插件特意制做成独立的控制台程序因为它用不着输入。这是一幅截图:
     源代码很小而且简单易懂,并且可以从上面的链接中获得。
     
          有两个关键的地方。第一是要使用多线程进行处理。我想让源代码在后台线程中编译因此它并不会影响Visual Studio UI. 但是要获取当前缓冲的文本你必须使用UI线程,而且要显示输出你也得使用它。我使用System.Timers.Timer在后台线程触发它的事件,同时 为需要UI线程的任务调用form.Invoke(…)。
          我还使用了“non-AutoReset”计时器。我让它获取源码并进行编译+运行+显示,暂停2秒后,再去获取源码并进行编译+运行+显示,如此循环。换句话说,计时器的时间间隔必须设为2 秒在处理完先前的定时事件之后。
    ''' <summary>
    ''' OnTimer 处理non-autoreset计时器信号。它运行在后台线程中。从当前的缓冲区中获取
    ''' 源代码并编译它,然后显示输出。
    ''' </summary>
    ''' <remarks></remarks>
    Sub OnTimer() Handles t.Elapsed
        Try
            Dim oldsrc = src
                    '我们在后台线程中。但只能从 UI 线程获取源...
            '此委托将获取源代码并将它存储在"src"字段中
            f.Invoke(New Action(AddressOf GetSource))
            If src <> oldsrc Then
                Dim oldoutput = output
                ' 在后台编译并运行
                output = CompileAndRun(src)
                If output <> "" OrElse oldoutput = "" Then
                    ' 在屏幕上显示输出必须在UI线程中完成
                    ' 此委托从"output"字段中得到要输出的内容并显示它
                    f.Invoke(New Action(AddressOf ShowOutput))
                End If
            End If
        Finally
            t.Start()
        End Try
    End Sub
         
           另一个关键时刻与如何运行代码并捕获它的输出有关。在“My”命名空间中,VB在这方面有很多有用的函数。我的主要问题是合理的处理异常不留任何遗漏。 (注意:获取临时文件名的代码并不完全准确:事实上你在某个状态之前得到一个未使用的临时文件名并不意味着这个文件名会一直不被使用;同样,它也并不意味 着添加了“.vb”扩展名的临时文件名会一直不被使用。但是把这种情况处理的更准确看直来并不十分划算;不管怎样,在异常处理中我们将所有的问题恢复到正 常状态。)
    Function CompileAndRun(ByVal src As String) As String
        Dim fn_exe = ""
        Dim fn_src = ""
        Dim vbc As System.Diagnostics.Process = Nothing
        Dim exe As System.Diagnostics.Process = Nothing
        Try
            ' 准备编译
            fn_src = My.Computer.FileSystem.GetTempFileName() & ".vb"
            My.Computer.FileSystem.WriteAllText(fn_src, src, False)
            fn_exe = My.Computer.FileSystem.GetTempFileName() & ".exe"
            Dim framework = Environment.ExpandEnvironmentVariables("%windir%\Microsoft.Net\Framework")
            Dim latest_framework = (From d In My.Computer.FileSystem.GetDirectories(framework) Where d Like "*\v*" Select d).Last
     
            ' 编译
            vbc = System.Diagnostics.Process.Start(New ProcessStartInfo _
                                With {.CreateNoWindow = True, _
                                      .UseShellExecute = False, _
                                      .FileName = latest_framework & "\vbc.exe", _
                                      .Arguments = String.Format("/out:""{0}"" /target:exe ""{1}""", fn_exe, fn_src)})
            Dim vbc_done = vbc.WaitForExit(3000)
            If Not vbc_done Then Return ""
            If vbc.ExitCode <> 0 Then Return ""
     
            ' 运行
            Dim pinfo = New ProcessStartInfo With {.CreateNoWindow = True, _
                                                   .UseShellExecute = False, _
                                                   .FileName = fn_exe, _
                                                   .RedirectStandardOutput = True}
            exe = New System.Diagnostics.Process With {.StartInfo = pinfo}
            exe.Start()
            Dim output = exe.StandardOutput.ReadToEnd
            Dim exe_done = exe.WaitForExit(3000)
            If Not exe_done Then Return ""
            Return output
        Finally
            ' 我们可以巧妙的关闭VBC进程
            If vbc IsNot Nothing Then
                If Not vbc.HasExited Then
                    Try : vbc.Kill() : Catch ex As Exception : End Try
                    Try : vbc.WaitForExit() : Catch ex As Exception : End Try
                End If
                Try : vbc.Close() : Catch ex As Exception : End Try
                vbc = Nothing
            End If
     
            ' 我们可以巧妙的关闭EXE
            If exe IsNot Nothing Then
                If Not exe.HasExited Then
                    Try : exe.Kill() : Catch ex As Exception : End Try
                    Try : exe.WaitForExit() : Catch ex As Exception : End Try
                End If
                Try : exe.Close() : Catch ex As Exception : End Try
                exe = Nothing
            End If
     
            ' 删除剩余的文件
            Try : My.Computer.FileSystem.DeleteFile(fn_exe) : Catch ex As Exception : End Try
            Try : My.Computer.FileSystem.DeleteFile(fn_src) : Catch ex As Exception : End Try
        End Try
    End Function
  • 相关阅读:
    Oracle基础知识整理
    linux下yum安装redis以及使用
    mybatis 学习四 源码分析 mybatis如何执行的一条sql
    mybatis 学习三 mapper xml 配置信息
    mybatis 学习二 conf xml 配置信息
    mybatis 学习一 总体概述
    oracle sql 语句 示例
    jdbc 新认识
    eclipse tomcat 无法加载导入的web项目,There are no resources that can be added or removed from the server. .
    一些常用算法(持续更新)
  • 原文地址:https://www.cnblogs.com/Leo_wl/p/2105295.html
Copyright © 2011-2022 走看看