В Objective C, почему это увеличивает 4 вместо 1?

В Objective C у меня есть простой блок кода, который увеличивает счетчик каждый раз, когда кнопка нажата. Мои журналы, и даже обновляют к интерфейсу, показывают инкремент 4 вместо одного. Это - просто проблема дисплея с моим форматированием (я использую %d), или что-то еще, что я пропускаю? Мое предположение находится с "%d", но я плохо знаком с Objective C и не уверен. (Отметьте, я также попробовал "счетчик + = 1"; с тем же результатом.

int counterValue = 0;
NSLog(@"Count at init: %d",counterValue);
...

-(IBAction)pushButton { 
    NSLog(@"Count (Pre-Push) = %d",counterValue);
    counterValue++;
    NSLog(@"Count (Post-Push) = %d",counterValue);
}

Вывод следующие:

2010-02-20 18:39:39.125 My App[37536:207] Count at init:  0
2010-02-20 18:39:39.845 My App[37536:207] Count (Pre-Push) = 0
2010-02-20 18:39:39.846 My App[37536:207] Count (Post-Push) = 4
2010-02-20 18:39:40.165 My App[37536:207] Count (Pre-Push) = 4
2010-02-20 18:39:40.166 My App[37536:207] Count (Post-Push) = 8
2010-02-20 18:39:40.727 My App[37536:207] Count (Pre-Push) = 8
2010-02-20 18:39:40.728 My App[37536:207] Count (Post-Push) = 12
18
задан bbum 23 February 2010 в 07:37
поделиться

1 ответ

Я бы не стал этого делать. Это нарушает инкапсуляцию и меняет контракт того, что ваш класс должен делать, не зная об этом реализаторов.

Если вы должны это сделать, однако, лучший способ - вызвать

class.getMethod("myMethod").getDeclaringClass();

Если возвращенный класс является вашим собственным, то он не переопределен; если это что-то другое, этот подкласс его переопределяет. Да, это отражение, но все еще довольно дешево.

Мне нравится ваш подход защищенного метода, хотя. Это выглядит примерно так:

public class ExpensiveStrategy {
  public void expensiveMethod() {
    // ...
    if (employOptimization()) {
      // take a shortcut
    }
  }

  protected boolean employOptimization() {
    return false;
  }
}

public class TargetedStrategy extends ExpensiveStrategy {
  @Override
  protected boolean employOptimization() {
    return true; // Now we can shortcut ExpensiveStrategy.
  }
}
-121--2303367-

Для этого нет прямого метода. Я написал этот патч обезьяны для ActiveRecord:: Base . Это будет работать для любого класса.

class ActiveRecord::Base

  def self.all_polymorphic_types(name)
    @poly_hash ||= {}.tap do |hash|
      Dir.glob(File.join(Rails.root, "app", "models", "**", "*.rb")).each do |file|
        klass = File.basename(file, ".rb").camelize.constantize rescue nil
        next unless klass.ancestors.include?(ActiveRecord::Base)

        klass.
          reflect_on_all_associations(:has_many).
          select{ |r| r.options[:as] }.
          each do |reflection|
            (hash[reflection.options[:as]] ||= []) << klass
          end
      end
    end
    @poly_hash[name.to_sym]
  end

end

Теперь вы можете сделать следующее:

Assignable.all_polymorphic_types(:assignable).map(&:to_s)
# returns ['Project', 'Event', 'Group']
-121--3133390-

Код, который вы показываете, не должен этого делать. Я сделал быструю программу, чтобы doublecheck, и я получаю ожидаемые результаты:

2010-02-22 17:04:35.787 app[68267:a0f] Count (Pre-Push) = 0
2010-02-22 17:04:35.790 app[68267:a0f] Count (Post-Push) = 1
2010-02-22 17:04:35.923 app[68267:a0f] Count (Pre-Push) = 1
2010-02-22 17:04:35.924 app[68267:a0f] Count (Post-Push) = 2

Я думаю, что вы затенены counterValue с другой переменной типа int * , которая делает + приращение на sizeof (int) , а не на 1.

43
ответ дан 30 November 2019 в 06:54
поделиться