只有通过3秒才能再次调用方法

时间:2016-01-26 11:59:04

标签: c# .net

我想实现某种方法来防止方法被立即多次调用。例如,假如我有一个类:

@reboot python /home/pi/x.py &

用户可以呼叫class Example { public void MyFunction() { // do something } } ,但仅限于自上次呼叫以来经过3秒。如果在3秒之前调用它,则不会发生任何事情(应忽略调用)。

我该怎么做?

编辑:

我不想使用MyFunction。我在考虑使用Thread.Sleep中的Timer类。但是我不知道如何根据自己的需要使用它。

4 个答案:

答案 0 :(得分:9)

我不认为有必要在这里使用计时器。您可以使用Stopwatch

class Example
{
    private static readonly TimeSpan MinInterval = TimeSpan.FromSeconds(3);
    private readonly Stopwatch stopwatch = new Stopwatch(); // Stopped initially

    public void MyFunction()
    {
        if (stopwatch.IsRunning && stopwatch.Elapsed < MinInterval)
        {
            return;
        }
        try
        {
            // Do stuff here.
        }
        finally
        {
            stopwatch.Restart();
        }
    }
}

请注意,此不是线程安全的...多个线程可以在同一个实例上同时执行该方法。每个实例都使用单独的秒表,因此多个线程可能会使用多个实例 - 如果要禁止跨所有实例的调用,则需要使用静态字段秒表,并且肯定会添加锁定以便安全地访问它。

另请注意,虽然您可以使用DateTime来检测上次执行时间,但通过用户更改系统时钟很容易出错。

这里使用try / finally是为了避免因快速连续的多次调用而导致异常被抛出。同样,这可能不是你想要的......你应该考虑是否希望在呼叫失败时重置秒表。

答案 1 :(得分:3)

您可以声明班级的私人DateTime字段,存储您的方法的最后通话时间,并检查与当前时间的差异:

class Example
{
    private DateTime _MyFunctionLastCallTime = DateTime.MinValue;
    private object _Lock = new object();

    public void MyFunction()
    {
        lock(_Lock)
        {
            var now = DateTime.UtcNow;
            if ((now - _MyFunctionLastCallTime).TotalSeconds < 3)
                return;

            _MyFunctionLastCallTime = now;
            // the rest of code
        }
    }
}

答案 2 :(得分:3)

使用Diagnostics.Stopwatch执行此操作:

class Program
{
    static Stopwatch stopwatch = new Stopwatch();
    static void Main(string[] args)
    {
        stopwatch.Start();
        Todo();
        Thread.Sleep(4000);
        Todo();
    }

    public static void Todo()
    {
        if(stopwatch.Elapsed.TotalSeconds > 3)
        {
            // do stuff
            stopwatch.Restart();
        }
    }
}

答案 3 :(得分:-2)

你不需要&#34;阻止&#34;任何事情也没有做任何与线程相关的事情,只是存储上次执行的时间并退出(或者抛出异常或做任何你想做的事情)如果它被调用的时间太短

private DateTime LastCalled;
public void MyFunc()
{         
    if (LastCalled > DateTime.Now.AddSeconds(-3)
    {
         return; // or do whatever else you want, throw an exception etc
    };
    LastCalled = DateTime.Now;
    // Your actual method code here
}