Skip to content
GitLab
Explore
Sign in
Primary navigation
Search or go to…
Project
S
stage_bastien_auvray
Manage
Activity
Members
Labels
Plan
Issues
Issue boards
Milestones
Wiki
Requirements
Code
Merge requests
Repository
Branches
Commits
Tags
Repository graph
Compare revisions
Snippets
Locked files
Build
Pipelines
Jobs
Pipeline schedules
Test cases
Artifacts
Deploy
Releases
Package registry
Container registry
Model registry
Operate
Environments
Terraform modules
Monitor
Incidents
Analyze
Value stream analytics
Contributor analytics
CI/CD analytics
Repository analytics
Code review analytics
Issue analytics
Insights
Model experiments
Help
Help
Support
GitLab documentation
Compare GitLab plans
Community forum
Contribute to GitLab
Provide feedback
Keyboard shortcuts
?
Snippets
Groups
Projects
Show more breadcrumbs
Bastien Auvray
stage_bastien_auvray
Commits
40aa263a
Commit
40aa263a
authored
2 years ago
by
Bastien Auvray
Browse files
Options
Downloads
Patches
Plain Diff
Upload New File
parent
d35edc1a
No related branches found
No related tags found
No related merge requests found
Changes
1
Show whitespace changes
Inline
Side-by-side
Showing
1 changed file
src/tests_swap.py
+258
-0
258 additions, 0 deletions
src/tests_swap.py
with
258 additions
and
0 deletions
src/tests_swap.py
0 → 100644
+
258
−
0
View file @
40aa263a
import
itertools
#Fonction outil pour calculer la parent distance.
#max_j(seq, i) trouve le plus grand entier j tq S[j] < S[i]
#et retourne j, ou retourne 0 si un tel j n'existe pas.
def
max_j
(
seq
,
i
):
j
=
0
for
k
in
range
(
0
,
i
):
if
seq
[
k
]
<
seq
[
i
]:
j
=
k
+
1
#+1 pour la numérotation
return
j
#Parent-distance classique, lue de la gauche vers la droite.
def
pdd
(
seq
):
res
=
[]
for
i
in
range
(
len
(
seq
)):
j
=
max_j
(
seq
,
i
)
if
j
!=
0
:
res
.
append
(
i
+
1
-
j
)
#+1 pour la numérotation
else
:
res
.
append
(
0
)
return
res
#Parent-distance de la droite vers la gauche, version paresseuse
#Il serait peut-être bon de la redéfinir comme pdd.
def
pdg
(
seq
):
s
=
seq
.
copy
()
list
.
reverse
(
s
)
res
=
pdd
(
s
)
list
.
reverse
(
res
)
return
res
#first_diff gauche et droite identifient la première position
#où les parent-distances diffèrent afin de mettre en évidence
#les deux indices sur lesquels le swap s'est possiblement produit.
#Chaque fonction renvoie l'indice de la première position qui diffère
#ou -1 si une telle position n'existe pas
def
first_diff_d
(
pdd1
,
pdd2
):
for
index
,
value
in
enumerate
(
zip
(
pdd1
,
pdd2
)):
if
value
[
0
]
!=
value
[
1
]:
return
index
return
-
1
def
first_diff_g
(
pdg1
,
pdg2
):
for
index
,
value
in
reversed
(
list
(
enumerate
(
zip
(
pdg1
,
pdg2
)))):
if
value
[
0
]
!=
value
[
1
]:
return
index
return
-
1
#Vérifie les conditions nécessaires (mais pas suffisantes)
#sur les éléments des parent-distances
#Voir pour factoriser le code plus tard
def
check_abcd
(
pdd1
,
pdd2
,
pdg1
,
pdg2
,
i
):
ad
=
pdd1
[
i
]
bd
=
pdd1
[
i
+
1
]
cd
=
pdd2
[
i
]
dd
=
pdd2
[
i
+
1
]
ag
=
pdg1
[
i
+
1
]
bg
=
pdg1
[
i
]
cg
=
pdg2
[
i
+
1
]
dg
=
pdg2
[
i
]
#cas x[i] < x[i+1]
if
(
bd
==
1
and
dg
==
1
):
if
((
ad
==
0
and
dd
!=
0
)
or
(
ad
>
0
and
(
cd
>
ad
or
dd
!=
ad
+
1
))
or
(
bg
==
0
and
cg
!=
0
)
or
(
bg
>
1
and
cg
!=
bg
-
1
)
or
(
bg
==
1
)):
return
False
#cas x[i] > x[i+1]
if
(
bg
==
1
and
dd
==
1
):
if
((
ag
==
0
and
dg
!=
0
)
or
(
ag
>
0
and
(
cg
>
ag
or
dg
!=
ag
+
1
))
or
(
bd
==
0
and
cd
!=
0
)
or
(
bd
>
1
and
cd
!=
bd
-
1
)
or
(
bd
==
1
)):
return
False
#Tout est cohérent sinon
return
True
#Vérifie si seq2 peut être CT-équivalente (à un swap près) à seq1
def
check_swap
(
seq1
,
seq2
):
pdd1
=
pdd
(
seq1
)
pdd2
=
pdd
(
seq2
)
pdg1
=
pdg
(
seq1
)
pdg2
=
pdg
(
seq2
)
i
=
first_diff_d
(
pdd1
,
pdd2
)
j
=
first_diff_g
(
pdg1
,
pdg2
)
if
i
==
-
1
or
j
==
-
1
:
return
False
diff
=
j
-
i
if
diff
==
1
:
return
check_abcd
(
pdd1
,
pdd2
,
pdg1
,
pdg2
,
i
)
if
diff
==
-
1
:
return
check_abcd
(
pdd1
,
pdd2
,
pdg1
,
pdg2
,
j
)
if
diff
==
0
:
return
(
check_abcd
(
pdd1
,
pdd2
,
pdg1
,
pdg2
,
i
-
1
)
or
check_abcd
(
pdd1
,
pdd2
,
pdg1
,
pdg2
,
i
))
return
False
#Fonction outil qui onstruit la séquence '1..n' qui permet
#d'ensuite générer toutes les permutations à l'aide d'itertools
def
seq_n
(
n
):
res
=
''
for
i
in
range
(
n
):
res
+=
str
(
i
+
1
)
return
res
#Brute force pour des permutations de taille n en effectuant
#toutes les poignées de mains possibles, puis retourne
#le nombre de matchs d'après check_swap ainsi que le nombre de
#poignées de main
#Décommenter la partie sur res permet de retourner une liste de
#toutes les permutations qui ont match en plus
def
check_all
(
n
):
perm
=
list
(
itertools
.
permutations
(
seq_n
(
n
)))
l
=
len
(
perm
)
check
=
0
handshake
=
0
#res = []
for
i
in
range
(
l
):
for
j
in
range
(
i
+
1
,
l
):
if
check_swap
(
list
(
perm
[
i
]),
list
(
perm
[
j
])):
check
+=
1
#res.append((i,j))
handshake
+=
1
return
check
,
handshake
#, res
#LEGACY CODE - USELESS AS OF NOW
# def check_swap_flag_or(seq1, seq2):
# pdd1 = pdd(seq1)
# pdd2 = pdd(seq2)
# pdg1 = pdg(seq1)
# pdg2 = pdg(seq2)
# i = first_diff_d(pdd1, pdd2)
# j = first_diff_g(pdg1, pdg2)
# if i == -1 or j == -1:
# return (False, False)
# diff = j - i
# if diff == 1:
# return (check_abcd(pdd1, pdd2, pdg1, pdg2, i), False)
# if diff == -1:
# return (check_abcd(pdd1, pdd2, pdg1, pdg2, j), False)
# if diff == 0:
# return ((check_abcd(pdd1, pdd2, pdg1, pdg2, i-1)
# or check_abcd(pdd1, pdd2, pdg1, pdg2, i)), True)
# return (False, False)
# def check_all_flag_or(n):
# perm = list(itertools.permutations(seq_n(n)))
# l = len(perm)
# check = 0
# handshake = 0
# res = []
# for i in range(l):
# for j in range(i + 1, l):
# ref = check_swap_flag_or(list(perm[i]), list(perm[j]))
# if (ref == (True, True)):
# check += 1
# res.append((i+1,j+1))
# handshake += 1
# return check, handshake, res
# def check_swap_flag_xor(seq1, seq2):
# pdd1 = pdd(seq1)
# pdd2 = pdd(seq2)
# pdg1 = pdg(seq1)
# pdg2 = pdg(seq2)
# i = first_diff_d(pdd1, pdd2)
# j = first_diff_g(pdg1, pdg2)
# if i == -1 or j == -1:
# return (False, False)
# diff = j - i
# if diff == 1:
# return (check_abcd(pdd1, pdd2, pdg1, pdg2, i), False)
# if diff == -1:
# return (check_abcd(pdd1, pdd2, pdg1, pdg2, j), False)
# if diff == 0:
# return ((check_abcd(pdd1, pdd2, pdg1, pdg2, i-1)
# ^ check_abcd(pdd1, pdd2, pdg1, pdg2, i)), True)
# return (False, False)
# def check_all_flag_xor(n):
# perm = list(itertools.permutations(seq_n(n)))
# l = len(perm)
# check = 0
# handshake = 0
# res = []
# for i in range(l):
# for j in range(i + 1, l):
# ref = check_swap_flag_xor(list(perm[i]), list(perm[j]))
# if (ref == (True, True)):
# check += 1
# res.append((i+1,j+1))
# handshake += 1
# return check, handshake, res
#-------------------------------------------
#TESTS
#list(itertools.permutations('012'))
#max_j(["5","6","1","3","4","2"], 4)
#max_j(('5','6','1','3','4','2'), 2)
#pdd(["4","5","6","1","2","7","8","3","9"])
#pdg(["4","5","6","1","2","7","8","3","9"])
#pdd(["4","5","6","3","1","7","8","2","9"])
#pdg(["4","5","6","3","1","7","8","2","9"])
#s1 = ["4","5","6","1","2","7","8","3","9"]
#s2 = ["4","5","6","3","1","7","8","2","9"]
#s3 = ("4","5","6","1","2","7","8","3","9")
#pd1 = pdd(s1)
#pd2 = pdd(s2)
#pd3 = pdg(s1)
#pd4 = pdg(s2)
#pd5 = pdd(s3)
#first_diff_d(pd1, pd2)
#first_diff_g(pd3, pd4)
#check_swap(s1, s2)
#check_swap(s1, s1)
#seq_n(3)
#list(itertools.permutations('1234'))
#l1 = check_all_flag_or(4)[2]
#l2 = check_all_flag_xor(4)[2]
#set(l1).symmetric_difference(set(l2))
#s4 = ["1","4","2","3"]
#s5 = ["3","2","1","4"]
#first_diff_d(pdd(s4), pdd(s5))
#first_diff_g(pdg(s4), pdg(s5))
#pdd(s4)
#pdd(s5)
#pdg(s4)
#pdg(s5)
#check_all_flag_or(4)
#check_all_flag_xor(4)
check_all
(
3
)
check_all
(
4
)
check_all
(
5
)
check_all
(
6
)
check_all
(
7
)
This diff is collapsed.
Click to expand it.
Preview
0%
Loading
Try again
or
attach a new file
.
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Save comment
Cancel
Please
register
or
sign in
to comment