# # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # #
# This is GNU Go, a Go program. Contact gnugo@gnu.org, or see #
# http://www.gnu.org/software/gnugo/ for more information. #
# Copyright 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, #
# 2008 and 2009 by the Free Software Foundation. #
# This program is free software; you can redistribute it and/or #
# modify it under the terms of the GNU General Public License #
# as published by the Free Software Foundation - version 3, #
# or (at your option) any later version. #
# This program is distributed in the hope that it will be #
# useful, but WITHOUT ANY WARRANTY; without even the implied #
# warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR #
# PURPOSE. See the GNU General Public License in file COPYING #
# You should have received a copy of the GNU General Public #
# License along with this program; if not, write to the Free #
# Software Foundation, Inc., 51 Franklin Street, Fifth Floor, #
# Boston, MA 02111, USA #
# # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # #
# Database of influence patterns.
# Q - same as O, plus sets the pattern anchor
# X - opposite color of O
# , - point which influence can't pass through
# ! - point where influence gets weakened when passing through
# (permeability multiplied by 0.7)
# ! - marks an intrusion for the anchor stone with indicated value
# Four different classes of patterns are used here.
# A - Patterns stopping O influence
# D - Patterns stopping X influence
# B - Intrusions (where O can intrude into X'x territory)
# t - Nonterritory patterns indicating points where one color cannot
# Constraints are as usual.
# B patterns are matched for the color to move, and for the color having
# made a move in followup influence, in order to compute the followup
# value of this move. (Only patterns including the played move or any
# stone saved by this move are taken into account.)
# For the followup influence, a pattern is used if the usual constraint
# is satisfied, and if the action returns true. See the influence
# documentation for explanation and influence.c for details.
#########################################################
# Influence blocking patterns (barriers) #
#########################################################
# gf Corrected symmetry. (3.1.23)
;!(oplay_break_through(a,b,c,b,d)==WIN)
;oplay_attack_either(a,b,c,a,c) || !oplay_attack_either(a,b,b,d)
# gf New pattern. (3.3.10)
;!safe_omove(a) || oplay_defend_both(a,b,c)
;!oplay_attack_either(a,b,b,c)
;(oplay_attack_either(a,b,f,a,f) || !oplay_attack_either(a,b,c,d))
;&& (oplay_attack_either(b,a,e,b,e) || !oplay_attack_either(b,a,c,d))
;(oplay_attack_either(a,b,f,a,f) || !oplay_attack_either(a,b,c,d))
;!oplay_attack_either(a,b,c,d)
;&& (oplay_attack_either(b,a,e,b,e) || !oplay_attack_either(b,a,c,d))
;!oplay_attack_either(a,b,c,d) && !oplay_attack_either(b,a,c,d)
;!oplay_break_through(a,b,c,a,c,d)
# gf Corrected symmetry. (3.1.23)
;!oplay_attack_either(a,b,c,a,c) || !oplay_attack_either(b,a,d,d,e)
;!oplay_attack_either(a,b,c,d,b,d) && !oplay_attack_either(d,c,b,a,c,a)
# This pattern could have '|' symmetry, but to improve the chances
# that it's matched before the expensive next one, we let it have
;!oplay_attack_either(a,b,c,d,b,d) && !oplay_attack_either(d,c,b,a,c,a)
;oplay_attack_either(a,b,c,d,b,d) || oplay_defend_both(a,b,c,d,a,c)
# gf Revised pattern. (3.5.3)
;!oplay_attack_either(a,b,c,d,b,d) && !oplay_attack_either(d,c,b,a,c,a)
;!oplay_attack_either(a,a,b)
;lib(A)>3 || (!legal_omove(b))
;|| (lib(A)>2 && (olib(b) <= 2 || oplay_attack_either(c,d,b,b,c)))
;!oplay_attack_either(a,b,c,a,c)
;oplay_defend_both(a,b,c,d,a,e)
;oplay_attack_either(a,b,b,D) || oplay_defend_both(a,b,a,c)
;oplay_attack_either(a,b,c,d,d,b) && !oplay_defend_both(a,c,b,c,E)
;lib(A)<=3 && lib(b)>=3 && lib(c)>=3
;lib(A)<=2 && lib(b)>1 && lib(c)>1
# gf New pattern. (3.3.10)
# gf New pattern. (3.3.10)
# gf New pattern. (3.3.13)
# gf New pattern. (3.5.3)
#########################################################
# Intrusion patterns (secondary influence sources) #
#########################################################
>return (lib(a)>2 || (lib(a) == 2 && connect_and_cut_helper(a,b,c)));
>return (lib(a)>2 || (lib(a) == 2 && connect_and_cut_helper(a,b,c)));
>return (lib(a)>2 || (lib(a) == 2 && connect_and_cut_helper(a,b,c)));
>return (lib(b)>2 || (lib(b) == 2 && connect_and_cut_helper(b,c,d)));
# ab New pattern (3.1.24).
>return (!xplay_attack(b,d));
# ab 3.1.22 Constraint added (see 13x13:52)
>return (!xplay_attack(b,d));
>return (!xplay_attack(a,d));
>return (!xplay_attack(b,d));
;!oplay_defend_both(a,b,c,D,E)
>return (!xplay_attack(b,f));
>return (!xplay_attack(b,a));
# >return (!xplay_attack(b,c));
;oplay_attack_either(a,b,C,b);
>return (!xplay_attack(b,c));
# ab 3.1.22 revised constraint (see territory valuation in 13x13:2)
;oplay_attack(a,B) && !attack(B)
>return (!xplay_attack(a,c));
;oplay_attack(a,B) && !attack(B)
>return (!xplay_attack(a,c));
# ab Modified action constraint. (3.3.20)
;oplay_attack_either(a,b,b,C)
>return (!xplay_attack(a,d) && o_somewhere(g,e,f,h));
# O can intrude on either side. The position of the influence source
# here isn't entirely accurate.
;oplay_attack(a,b,b) && oplay_attack(c,d,d)
# O can intrude on either side. The position of the influence source
# here isn't entirely accurate.
;oplay_attack(a,b,b) || oplay_attack(c,d,d)
;o_somewhere(b) || oplay_attack_either(a,b,b,C)
>return (!xplay_attack(b,d));
;oplay_attack_either(a,b,c,d,b,d)
>return (lib(d)>2 && lib(e)>2 && !xplay_attack(a,e));
# ab value decreased (3.1.24)
# ab value decreased (3.1.24)
>return (!xplay_attack(a,b));
;lib(A)==2 && !oplay_attack(b,b)
>return (!xplay_attack(c,d) && xplay_defend_both(e,d,f));
>return (!xplay_attack(a,b));
>return (!xplay_attack(a,b));
>return (!xplay_attack(a,b));
;oplay_attack_either(a,b,c,d,b,d)
>return (!xplay_attack(b,e));
>return (!xplay_attack(a,b));
;oplay_attack_either(a,b,c,d,b,d)
;oplay_attack(a,b,c,d,e,f,f)
>return (!xplay_attack(b,c))
>return (!xplay_attack(a,b));
>return (!xplay_attack(a,b));
;oplay_attack(a,b,c,d,e,f,d)
>return (!xplay_attack(a,b));
> return (!xplay_attack(a,b));
> return (!xplay_attack(a,b));
>return (!xplay_attack(a,b));
# gf Revised constraint. (3.3.10)
;(o_somewhere(e) || !safe_xmove(e)) && !oplay_defend(a,b,c,D)
;lib(A)==2 && !attack(A) && !oplay_attack(b,c,d,d)
# gf New pattern. (3.1.20)
;&& (o_somewhere(e) || oplay_attack(a,e,e))
;&& !oplay_defend_both(a,b,c,b,D)
>return (!xplay_attack(a,f) && (o_somewhere(e) || (!xplay_attack(e,f))));
# ab New pattern. (3.3.5)
;&& (o_somewhere(b) || oplay_attack(a,b,b))
;&& !oplay_defend_both(a,c,d,e,F,G)
>return (!xplay_attack(a,h));
# gf New pattern. (3.1.20)
;safe_omove(a) && oplay_attack(a,b,C)
# gf New pattern. (3.1.22)
# gf Fixed diagram inconsistency. (3.1.23)
# FIXME: This pattern exaggerates the intrusion since X can stop it
# on one of the sides, but we don't know which one he will
# choose. This may or may not be a problem in practice.
# gf New pattern. (3.1.23)
# ab New pattern. (3.1.23)
# FIXME: This would need a constraint. The one below did not work.
# ;oplay_attack(a,b,c,d,e,f,f)
;oplay_attack(a,b) && ! attack(b)
>return (!xplay_attack(a,c));
;!oplay_attack_either(a,b,c,c,d)
;oplay_break_through(a,b,C,b,D)
>return(!xplay_attack(a,e));
# ab New pattern. (3.3.5)
# This is a bit incorrect, as usually X can choose on which side the
# intrusion is allowed to happen.
# Due to reading depth limitations, oplay_break_through == CUT is not
# sufficient (see nngs1:40).
# pp Revised constraint (3.5.1)
# Ko checks prevent 0.5 point "breaks through" with no further threat.
; (oplay_break_through(a,b,c)==WIN
; && (!ko(a) || oplay_attack_either(d,b,c))
; && (!ko(c) || oplay_attack_either(e,b,a)))
# gf New pattern. (3.3.3)
>return (!xplay_attack(a,b));
# gf New pattern. (3.3.3)
# ab New pattern (3.3.10)
# X cannot play double hane.
;(o_somewhere(a) || o_somewhere(b) || o_somewhere(c))
;&& (o_somewhere(a) || oplay_attack(d,a,a)) && oplay_attack(e,f,G)
# gf New pattern (3.3.16)
;x_somewhere(b,c,d,e,f,g) && safe_omove(a)
# gf New pattern (3.3.16)
;x_somewhere(c,d,e,f,g,h) && !oplay_disconnect(a,a,b)
# gf New pattern (3.3.16)
>return !xplay_attack(a,b);
# gf New pattern (3.3.17)
;!oplay_disconnect(f,g) && !oplay_disconnect(a,b,c,d,e,c,f)
# It is a little drastic, but see arend2:120 for where it is necessary.
;!attack(A) && oplay_disconnect(A,B) && !attack(B)
# gf FIXME: This pattern looks rather likely to introduce more
# problems than it solves. We may need to find some other
# solution to endgame:880. (3.5.7)
OQ? this pattern should prevent attempts to cut bamboo joint
# gf New pattern. (3.5.2)
# This pattern is somewhat questionable. See arend:30 and 13x13:16 for
# positions where it helps.
;!oplay_connect(a,b,c,D,E)
# gf New pattern. (3.5.3)
>return !safe_xmove(a) && !oplay_defend_both(c,b,a,b,D);
# gf New pattern. (3.7.10)
# Try to discourage unreasonable hane. See gunnar:85.
;olib(a)>1 && !oplay_connect(a,b,c,b,D)
#########################################################
# Nonterritory patterns #
#########################################################
# gf Revised constraint. (3.3.10)
>if (!false_eye_territory(a)) non_oterritory(a);
>if (!false_eye_territory(b)) non_xterritory(b);
# gf Revised constraint. (3.3.10)
# gf Revised constraint. (3.3.17)
>if ((halfeye(a) || false_eye(a)) && safe_omove(b)
> && !false_eye_territory(a)) non_xterritory(a);
# gf Revised constraint. (3.3.10)
> && !false_eye_territory(a)) non_oterritory(a);
# gf Revised constraint. (3.3.10)
>if (!false_eye_territory(a)) non_xterritory(a);
# gf Revised constraint. (3.3.10)
>if (!false_eye_territory(a)) non_oterritory(a);
# gf Revised constraint. (3.3.10)
>if (!false_eye_territory(a)) non_oterritory(a);
>if (!false_eye_territory(b)) non_xterritory(b);
# gf The old constraint was no good, as can be seen in nngs1:40. After
# black R6 this pattern declared S5 non-territory. (3.1.30)
;safe_omove(a) && oplay_attack(a,b,c,a) && connect_and_cut_helper2(a,b,c)
;!oplay_defend_both(a,b,c,b,D)
# gf New pattern. (3.3.7)
;safe_omove(a) && !oplay_defend_both(a,b,c,?,d,b,E)
;safe_omove(a) && oplay_attack(a,B)
;!oplay_defend_both(a,b,?,c,a,d)
# gf New pattern. (3.3.7)
;!xplay_defend_both(a,b,c)
;!oplay_defend_both(a,b,c,?,d,b,E)
;!oplay_defend_both(a,b,c,d,e,?,f,d,b)
# gf New pattern. (3.1.18)
;oplay_attack(*,a,a) && safe_omove(*)
# gf New pattern. (3.1.18)
;attack(b) && oplay_attack(*,b)
;!oplay_attack(a,b,b) && !oplay_attack(b,a,a)
# tm New Pattern (3.1.20)
# tm New Pattern (3.1.20)
# gf New pattern. (3.1.20)
;lib(A)==2 && connect_and_cut_helper(A,b,c)
# gf New pattern. (3.1.20)
# gf New Pattern (3.1.22)
# gf New Pattern (3.1.22)
# gf New pattern. (3.1.23)
;!safe_omove(a) && oplay_attack(b,a,b)
# gf New pattern. (3.1.23)
;oplay_attack(a,b,b) && !oplay_attack(a,c,b,b) && oplay_attack(a,c,b,E)
# gf New pattern. (3.1.23)
;oplay_attack(a,b,b) && oplay_attack(a,c,b,c)
# gf New pattern. (3.1.23)
# gf This pattern is somewhat problematic. O can often block at d to
# secure e or block at b to secure c. The real point of the pattern
# is that O can't secure both, but there's no way to express this
# accurately. See gunnar:15 for a position where this pattern is
;!oplay_attack(a,b,c,d,e,d)
# gf New pattern. (3.1.30)
;!oplay_attack(a,b,c,a) && !oplay_attack(a,c,b,a)
# gf New pattern. (3.1.30)
;&& ((x_somewhere(b) && oplay_attack(a,b))
; || (!x_somewhere(b) && oplay_attack(a,b,b)))
# gf New pattern. (3.3.4)
;!oplay_attack(a,b,c,a) && !oplay_attack(a,c,b,a)
# gf New pattern. (3.3.7)
# gf Revised constraint. (3.3.10)
# gf New pattern. (3.3.10)
;lib(B)==3 && safe_omove(a) && oplay_attack(a,B)
# gf New pattern. (3.3.10)
;!xplay_defend_both(a,b,c)
# gf New pattern. (3.3.10)
;!oplay_defend_both(a,?,b,C,D)
# gf New pattern. (3.3.10)
;!oplay_defend(a,b,c,d,a)
# gf New pattern. (3.3.13)
# gf New pattern. (3.3.15)
;!xplay_defend_both(a,b,c) && !adjacent_to_defendable_stone_in_atari(b)
;&& !adjacent_to_defendable_stone_in_atari(c)
# gf New pattern. (3.3.15)
;!oplay_attack(b,D) && !oplay_attack(b,c,c)
# gf New pattern. (3.3.15)
;oplay_attack(a,b,c) && !oplay_attack(b,d,d)
# gf New pattern. (3.3.16)
;lib(C)==2 && safe_omove(a) && oplay_attack(a,C) && !oplay_attack(a,b,a)
# gf New pattern. (3.3.17)
;oplay_defend(a,b,c,d,e,f,a)
# gf New pattern. (3.3.17)
;!oplay_attack(a,C) && !oplay_attack(b,D)
# gf New pattern. (3.5.3)
;!oplay_defend_both(a,b,a,c)
# gf New pattern. (3.5.3)
;!oplay_attack(a,b,c,a) && !oplay_attack(a,c,b,a)
# gf New pattern. (3.5.3)
;!oplay_attack(a,b,c,a) && !oplay_attack(a,c,b,a)
# gf New pattern. (3.5.3)
;!safe_omove(a) && !oplay_defend_both(b,a,?,c,b,d)
# gf New pattern. (3.5.3)
;lib(C)==2 && !adjacent_to_stone_in_atari(C) && !oplay_attack_either(a,a,b)
# gf New pattern. (3.5.3)
;oplay_attack(a,b,b) && !oplay_attack_either(a,a,c)
# gf New pattern. (3.5.3)
;oplay_defend_both(a,b,c,D,b) && oplay_attack(a,b,a)
# gf New pattern. (3.5.4)
;!oplay_attack(a,b,c,a) && !oplay_attack(a,d,c,a)
# gf New pattern. (3.7.1)
# gf New pattern. (3.7.1)
;safe_omove(a) && oplay_attack(a,b,c,d,b)
# gf New pattern. (3.7.2)
;!oplay_attack_either(a,c,D,c) && !oplay_attack_either(c,a,E,a)
# gf New pattern. (3.7.2)
;!oplay_attack_either(a,c,D,c) && !oplay_attack_either(c,a,E,a)
# gf New pattern. (3.7.2)
;!oplay_attack_either(a,c,D,c) && !oplay_attack_either(c,a,E,a)