2015-04-12 5 views
-2

Я делаю три случайных выбора между двумя классами, A и B. Мне нужно избегать получения B все три раза.Есть ли способ установить ограничения на результаты arc4random()?

Есть ли способ остановить arc4random() от предоставления мне этого результата?

+1

Итак, если вы получаете два узла типа b, тогда вы должны вручную сделать третий узел типа a, минуя в этом случае RNG. – Petesh

+2

'arc4random' не проблема. Он ничего не отображает. Он просто дает число. Вам просто нужно настроить свою логику, чтобы у вас всегда был хотя бы один «а» узел. – rmaddy

+0

[Как получить не вдвое большее значение в строке?] (Http://stackoverflow.com/q/13745248) –

ответ

3
  • Один из подходов: Если ваша случайная процедура дает вам неприемлемый ответ, запустите его снова, пока он не даст вам приемлемый ответ.

    Например, в приложении для игры в пасьянс я перетасовываю колоду и обрабатываю ее часть в макет, который должен быть разрешен. Но что, если оно не разрешимо? Я повторяю это: я снова перетасовываю палубу и обрабатываю ее снова. Я продолжаю делать это до тех пор, пока макет, который я получил , не является разрешимым. Все это происходит до того, как пользователь что-либо видит, поэтому пользователь не знает, за что я был за кулисами, чтобы гарантировать, что макет имеет смысл.

  • В вашем случае, когда возможности настолько ограничены, другой очевидной альтернативой было бы следующее: использовать простой комбинаторный алгоритм для генерации заранее всех приемлемых комбинаций из трех узлов. Теперь используйте arc4random, чтобы выбрать одну из этих комбинаций. Так, например:

    var list = [[String]]() 
    let possibilities = ["A","B"] 
    for x in possibilities { 
        for y in possibilities { 
         for z in possibilities { 
          list.append([x,y,z]) 
         } 
        } 
    } 
    list.removeLast() 
    

    Теперь list представляет собой массив из всех возможных троек "A" или "B", но без [ "B", "B", "B"]. Итак, теперь выберите элемент случайным образом и для каждого из его букв, если это «A», используйте класс A, а если он «B», используйте класс B. (Конечно, я полагаю, что мы могли бы сделать это с помощью реальных классов или случаи, но это, кажется, проще кодировать его в виде писем.)

0

BOOLS и петли на помощь ...

BOOL classA = false; 
BOOL classB = false; 

for (int i=0; i<3; i++) { 

    int r = arc4random() % 2; 

    if(i < 2) { 
     if(r == 0) { 
      NSLog(@"Class A"); 
      classA = true; 
     } else { 
      NSLog(@"Class B"); 
      classB = true; 
     } 
    } else { 
     if(classA == false) 
      NSLog(@"Class A"); 
     if(classB == false) 
      NSLog(@"Class B"); 
    } 
} 

2 BOOLS гарантируют, что каждый класс имеет по меньшей мере один элемент для каждые три цикла.

+1

FYI - используйте 'YES' и' NO' с 'BOOL', а не' true' и 'false'. – rmaddy

+0

@rmaddy - В чем разница в контексте выше? Я использую true/false в течение некоторого времени без проблем. – sangony

+0

Это немного педантично, и, в конце концов, они, вероятно, все означают одно и то же, но «BOOL» специфичен для Objective-C и предназначен только для двух значений: «NO» и «YES». 'true' и' false' предназначены для использования с разными типами. – rmaddy