查找翻译表


17

给定两个字符串,找到两者之间的转换表(替换密码),如果无法转换,则输出false。必须最小化并从左到右创建答案。单词之间要翻译的第一个字符必须是翻译表中的第一个字符。除此之外,任何未翻译的字母(与原始位置相同)都不应出现在翻译表中。

通过示例可能最容易定义:

有效案例

"bat", "sap" => ["bt","sp"]

请注意顺序,["tb","ps"]此挑战的输出无效。

"sense", "12n12" => ["se","12"]

请注意,n由于它是一对一的关系,因此不翻译。

"rabid", "snail" => ["rabd","snal"]

请注意,i由于它是一对一的关系,因此不翻译。

"ass", "all" => ["s","l"]

不包括A,它保持不变,由于模式匹配而s可以映射到l

"3121212", "ABLBLBL" => ["312","ABL"]

完美匹配图案。

虚假案件

"banana", "angular" => false

(长度不一样,不可能)。

"animal", "snails" => false

(每个字符只能在翻译的每一侧一次使用)。

"can","cnn" => false

(n在翻译中隐式使用,因此,使用n-> a定义翻译表将无效)

因此,这[aimal,sails]是一个无效的答案,这很虚假。

"a1", "22" => false

参见“腔室”,列为虚假的。在这种情况下,是因为a1都不能同时映射到2。(每个字符只能在翻译的每一侧一次使用)。


这个答案似乎是一个很好的基准:https : //codegolf.stackexchange.com/a/116807/59376

如果您对两个未列出的单词对的功能有疑问,请遵循此实现。


I / O规则

  • 输入可以是2元素数组或2个单独的输入。
  • 输出可以是数组或换行符/空格分隔,类似于我显示的方式。
  • 错误输出可能是0,-1或false。错误/空输出也可以。
  • 您将保证这a将不相等ba也不b为空。
  • a并且b是仅可打印ASCII的字母序列。

注意事项

  • 翻译必须从左到右进行,请参见示例1。
  • 您不得输出保持相同的字符。
  • 您的程序只能包含两个字符串ab
  • 每个字符只能在翻译的每一面一次使用。这就是使翻译从不可能snails变为animals不可能的原因。
  • 不应进行递归替换。递归替换的示例:"a1","22"->[a1,12]首先将a替换为1,然后将两个结果1都替换为2。这是不正确的,假设所有翻译都是彼此独立发生的,这是虚假的。含义:转换表为[a1,12]的“ a1”计算为12(而不是22)

将这个“翻译”标记为简单的替换密码可能有助于阐明其意图。
格雷格·马丁

是否允许关联数组作为输出?它可以挽救我一些字节
约尔格Hülsermann

@JörgHülserman我不太确定允许这样做的含义,也许要制作两个版本,以便我能看到区别?如果我认为对挑战没有害处,我将对其进行编辑。
魔术章鱼缸

看我交第一溶液作为串和第二个有作为输出关联数组
约克Hülsermann

@JörgHülsermann嗯...我明白了您现在如何使用它,我想我不允许这样做,并非所有语言都支持类似哈希的结构。
Magic Octopus Urn

Answers:


7

JavaScript(ES6),128个字节

f=
(s,t)=>!t[s.length]&&[...s].every((c,i)=>n[d=t[i]]==c||d&&!m[c]&&!n[d]&&(n[m[c]=d]=c,c==d||(a+=c,b+=d)),m={},n={},a=b='')&&[a,b]
<div oninput=o.textContent=f(s.value,t.value)><input id=s><input id=t><pre id=o>


不适合工作assall,应该是s,l
Magic Octopus Urn

是的,那段代码是绊脚石,也得到了验证,这很好。
Magic Octopus Urn

1
@carusocomputing这是一个变量名冲突-现在已修复。对于那个很抱歉。
尼尔

7

的JavaScript(ES6),108个 107 105 106字节

编辑:修复了支持"22" / "a1"虚假的输入的问题。


返回0两个字符串之一或一个数组。

f=(a,b,x)=>[...a].some((c,i)=>d[C=b[i]]?d[C]!=c:(d[C]=c)!=C&&(s+=c,t+=C,!C),s=t='',d=[])?0:x||f(b,a,[s,t])

格式化和评论

f = (                       // given:
  a,                        // - a = first string
  b,                        // - b = second string
  x                         // - x = reference result from previous iteration,
) =>                        //       or undefined
  [...a].some((c, i) =>     // for each character c at position i in a:
    d[                      //   if we already have a translation
      C = b[i]              //   of the character C at the same position in b,
    ] ?                     //   then:
      d[C] != c             //     return true if it doesn't equal c
    :                       //   else:
      (d[C] = c) != C &&    //     store the translation C -> c in the dictionary
      (                     //     if the characters are different:
        s += c, t += C,     //       append them to the translation strings s and t
        !C                  //       return true if C is undefined
      ),                    //
    s = t = '', d = []      //   initialize s, t and d  
  ) ?                       // if some() returns true:
    0                       //   there was a translation error: abort
  :                         // else:
    x ||                    //   if this is the 2nd iteration, return x
    f(b, a, [s, t])         //   else do a recursive call with (b, a)

测试用例


f('22')('a1')也应该是虚假的。
Neil

希望这次我做对了。
Arnauld

1
当您的错误修正简化为更短的代码时,它总是很方便的!
尼尔,

7

PHP> = 7.1,130字节

@Titus保存的18个字节

for([,$x,$y]=$argv;a&$o=$y[$i];)$o==($p=$x[$i++])?:$k[$c[$p]=$o]=$p;echo$y==strtr($x,$c)&$x==strtr($y,$k)?join($k)." ".join($c):0;

测试用例

展开式

for([,$x,$y]=$argv;a&$o=$y[$i];)
$o==($p=$x[$i++])?:$k[$c[$p]=$o]=$p; # if char string 1 not equal char string 2 make key=char1 value=char2 and key array
echo$y==strtr($x,$c) # boolean replacement string 1 equal to string 2
    &$x==strtr($y,$k) # boolean replacement string 2 equal to string 1
    ?join($k)." ".join($c) # output for true cases
:0; #Output false cases

PHP> = 7.1,148字节

打印0表示false输出true作为字符串

for([,$x,$y]=$argv;a&$o=$y[$i];$i++)$x[$i]==$o?:$c[$x[$i]]=$o;echo$y==strtr($x,($f=array_flip)($k=$f($c)))&$x==strtr($y,$k)?join($k)." ".join($c):0;

测试用例

展开式

for([,$x,$y]=$argv;a&$o=$y[$i];$i++)
$x[$i]==$o?:$c[$x[$i]]=$o; # if char string 1 not equal char string 2 set key=char1 value=char2
echo$y==strtr($x,($f=array_flip)($k=$f($c))) # boolean replacement string 1 equal to string 2
&$x==strtr($y,$k) # boolean replacement string 2 equal to string 1
    ?join($k)." ".join($c) # output for true cases
:0; #Output false cases

PHP> = 7.1,131字节

如果允许关联数组,则可以将第二个答案简称为

将0打印为false,将true输出为关联数组而不是字符串

for([,$x,$y]=$argv;a&$o=$y[$i];$i++)$x[$i]==$o?:$c[$x[$i]]=$o;print_r($y==strtr($x,($f=array_flip)($f($c)))&$x==strtr($y,$k)?$c:0);

测试用例

PHP> = 7.1,227字节

打印0为假

[,$x,$y]=$argv;echo strlen($x)==strlen($y)?strtr($x,$c=array_filter(($f=array_flip)($z=$f(array_combine(($p=str_split)($x),$p($y)))),function($v,$k){return$k!=$v;},1))==$y&$x==strtr($y,$z)?join(array_keys($c))." ".join($c):0:0;

测试用例

展开式

[,$x,$y]=$argv; # 
echo strlen($x)==strlen($y) #compare string lengths
?strtr($x,  # replace function
$c=array_filter( # filter 
($f=array_flip)($z=$f( # # remove doubles like in testcase: a1 => 22
    array_combine(($p=str_split)($x),$p($y))  # replacement array keys string 1 values string 2 
))
    ,function($v,$k){return$k!=$v;},1)) # remove all keys that equal to values in array
    ==$y # boolean replacement string 1 equal to string 2
&$x==strtr($y,$z) # boolean replacement string 2 equal to string 1        
?join(array_keys($c))." ".join($c) # output for true cases
    :0 # Output if replacement from string 1 is not equal to string 2
:0; #Output for different lengths

1
@carusocomputing谢谢你的夸奖。我忘了一个小把戏。我知道这里有很多人他们是更好的,然后我
约尔格Hülsermann

2
您绝对擅长于找到解决方案+1,但array_values()内部join()完全没有用,可以丢弃。
Christoph'Apr

1
这使a1 22 => false测试用例失败。另外,您的第一个程序似乎无法在在线测试仪中运行。
mbomb007 '17

1
闭嘴。太棒了。
泰特斯

1
脚蹼可以:($p=$x[$i])==$o?:$k[$c[$p]=$o]=$p;在循环中保存18个字节,并$y==strtr($x,$c)进行第一次测试。
泰特斯

5

果冻,18 字节

ẠaQ⁼µ€Ạ
z0EÐḟQZẋÇ$

未命名的单子链接(单输入功能)带有一个列表,该列表返回:
在false情况下为空列表;或
在真实情况下包含两个字符列表的列表。

在线尝试!(页脚用空格分隔列表,以避免打印模糊的表示形式)
...或查看测试套件

怎么样?

ẠaQ⁼µ€Ạ - Link 1, valid?: mapping list
    µ€  - perform the code to the left for €ach mapping entry
Ạ       -     none of mapping entry falsey? (this & Main's z0 handle unequal input lengths)
  Q     -     deduplicate mapping entry
   ⁼    -     is equal to mapping list? (non-vectorising)
 a      -     and
      Ạ - none falsey (both mapping lists must pass that test)
        - The whole function returns 1 if the mapping list is acceptable, 0 if not

z0EÐḟQZẋÇ$ - Main link: list of strings
z0         - transpose with filler 0 (unequal lengths make pairs containing zeros)
   Ðḟ      - filter discard:
  E        -     all equal? (removes the untranslated character pairs)
     Q     - deduplicate (removes the repeated translation pairs)
      Z    - transpose (list of pairs to pair of lists)
         $ - last two links as a monad:
       ẋ   -     repeat list this many times:
        Ç  -         call last link (1) as a monad

5

视网膜194个 191 185 229 225 241字节

.+
$&;$&
+`^\w(\w*;)\w
$1
^;\w.*|.+;;.*|;;

^((.)*)(.)(.*;(?<-2>.)*(?(2)(?!)))\3
$1$4
+`((.)(.)*)\2((.)*;.*(.)(?<-3>.)*(?(3)(?!)))\6((?<-5>.)*(?(5)(?!)))$
$1$4$7
^(.)*(.)(.)*(\2)?.*;(?<-1>.)*(?(1)(?!))(.)(?<-3>.)*(?(3)(?!))(?(4)(?!\5)|\5).*

在线尝试!

接受输入- ;分隔。输出也;分开。错误的输入由空的输出表示。

我知道这很痛苦,我仍在尝试减少字节数。这些字节中的大多数都用于删除错误的输入。

编辑

  • 事实证明,我的程序存在严重缺陷。现在已修复,但代价是超过40个字节。

  • 发现了另一个错误,该错误是我的程序未将输入声明为a1;22false,但修复该程序后,它可以将程序保持在250字节以下

说明

(稍后将进行更详细的说明)

首先,我们必须检查字符串的长度ab是否相同。如果不是,我们将删除所有内容。

在进行长度测试时,复制输入以保留它。

.+                      Matches everything
$&;$&                   $& indicates the match, so $&;$& will duplicate the match and separate it with a semi-colon

现在,在循环中,我们删除的第一个字符a和的第一个字符,b直到其中一个字符串为空。

+`                     Repeatedly (until no more substitutions could be made) replace
  ^\w                   A word character (letter or number) at the beginning
     (\w*;)             Capture Group 1: matches any number of word characters and a semicolon
           \w           And a word character after the semi-colon
                       with
$1                      The result of the first capture group

现在有“模式空间”的可能性。

  • ;;abc 两根弦的长度相等
  • def;;abc a 超过 b
  • ;def;abc b 超过 a

现在,如果字符串的长度不同(场景2和3),我们就必须清空输入。这就是下面的替换所做的。它删除与方案2和3匹配的文本。

^;\w.*|.+;;.*|;;

这将删除未在字符串a和中音译的字符babc;1b2=>ac;12

^((.)*)(.)(.*;(?<-2>.)*(?(2)(?!)))\3
$1$4

之后,我们必须删除重复的字符。sese;1212=> se;12,但是这样保留输入aba;123

+`((.)(.)*)\2((.)*;.*(.)(?&lt;-3&gt;.)*(?(3)(?!)))\6((?&lt;-5&gt;.)*(?(5)(?!)))$
$1$4$7

最后,如果有重复的字符映射到不同的字符(例如aba;123或),我们将删除输入a1;22

^(.)*(.)(.)*(\2)?.*;(?.)*(?(1)(?!))(.)(?.)*(?(3)(?!))(?(4)(?!\5)|\5).*

最后,删除重复的字符。


使用这些平衡组,我看到了!
尼尔,

@尼尔确实!我也使用了(?(1)(?!))从您的回答中学到的知识:)
Kritixi Lithos

我不知道先删除重复项然后验证剩余的集合是否会短一些-在字母的每一面上剩下的每个字母之一;
尼尔,

@Neil我的代码尝试此操作时发现错误。早上我会进一步研究。
Kritixi Lithos

4

果冻28 26字节

QL$€⁼L€
EÐḟQZK0Ç?
ZÇ0L€E$?

在线尝试!

QL$€⁼L€      Checks validity of mapping
QL$€          number of unique characters in mapping
    ⁼         equals
     L€       number of characters in mapping

EÐḟQZK0Ç?  Writes valid mapping or 0
EÐḟ           filter maps where a = b
   Q          filter duplicate maps
    Z         zip by column [["ac"],["bd"]] => ["ab","cd"]
     K0Ç?   print if valid map, else print 0

ZÇ0L€E$?      main link: takes an array of 2 strings
Z              zip by column: ["ab", "cd"] => [["ac"],["bd"]]
 Ç     ?       print mapping if
   L€E$         all pairs are same length (returns 0 if initial strings were
  0             else 0

1
欢迎来到PPCG!如何地狱,你已经知道果冻只有21分?非常令人印象深刻!
魔术章鱼缸

2
谢谢。环顾四周,似乎是一种精巧的语言。
–layagyasz

05AB1E是另一个易于尝试的有趣尝试。
魔术章鱼缸

3

Ruby,133个字节

->a,b{a.size!=b.size||(m=a.chars.zip b.chars).any?{|i,j|m.any?{|k,l|(i==k)^(j==l)}}?0:m.select{|x,y|x!=y}.uniq.transpose.map(&:join)}

在线尝试!

更具可读性:

->a, b{
    # Pair the letters in each string - [AB, AB, AB,...]
    pairs = a.chars.zip(b.chars)

    # If there's any combination of two pairs that share one character but not both,
    # or if the strings have different lengths, then the input's invalid.
    if a.size != b.size || pairs.any?{|i,j| pairs.any? {|k, l| (i==k)!=(j==l) }} 
        return 0 # 0 isn't actually falsy in Ruby, but this challenge allows it anyway
    end
    return pairs.select{|x,y| x != y} # Remove unchanged letters
                .uniq                 # Remove duplicates
                .transpose            # Change [AB, AB, AB] form to [AAA, BBB] form.
                .map(&:join)          # Convert the arrays back into strings
}

只是为了踢球,这是Goruby中的一个84字节版本,它是Ruby,但是在编译解释器时设置了golf标志。除其他事项外,它允许您将方法调用缩写为其最短的唯一标识符。

->a,b{a.sz!=b.sz||(m=a.ch.z b).ay?{|i,j|m.y?{|k,l|(i==k)^(j==l)}}?0:m.rj{|x,y|x==y}.u.tr.m(&:j)}

为什么不通过Goruby实现发布第二个答案?这不是一种公认​​的高尔夫语言吗?
魔术章鱼缸

@carusocomputing完全是;在我看来,它似乎并没有自己的答案-与我的主要答案完全相同,只是方法名称缩写。也许,如果我找到一种方法来利用Goruby的更多差异,我会单独发布答案。
Tutleman '17

3

Python 2中198,193,189,182,179,175,169, 165个字节

def f(a,b):
 r=([""]*2,0)[len(a)!=len(b)]
 for u,v in zip(a,b):
	if r:
		q,w=r
		f=q.find(u)
		if u!=v:r=(([q+u,w+v],r)[f>-1 and w[f]==v],0)[f<0 and v in w]
 print r

在线尝试!

  • -4字节!感谢mbomb007建议使用制表符而不是空格。

  • 再次感谢mbomb007修改了输入格式。


你是什​​么意思?请停止进行不必要的修改,这些修改不会增加任何价值!
Keerthana Prabhakaran

选项卡保存约4个字节!谢谢!
Keerthana Prabhakaran


我使您的程序在同一行上包含每个测试用例,这对测试您的程序的任何人都非常有帮助。
mbomb007 '17

如果您能在编辑评论中提到这一点,我会更好的!
Keerthana Prabhakaran

3

Python 3.6、211 185 181 178字节

退出并显示错误结果。

def f(x,y,d={}):
    for a,b in zip(x,y):1/(a not in d or b==d[a]or len(x)-len(y));d[a]=b;1/([*d.values()].count(b)<2)
    return map(''.join,zip(*[x for x in d.items()if x[0]!=x[1]]))

这需要Python 3.6,您可以在shell中运行它 此处

您可以在此处进行测试,而无需在TIO上进行正确的输出排序。(TIO没有3.6)。

取消高尔夫:

from collections import*
d=OrderedDict()                     # keep order
x,y=input()
if len(x)!=len(y):1/0               # equal lengths
for a,b in zip(x,y):
    if a in d and d[a]!=b:1/0       # no duplicate keys
    else:d[a]=b
    if d.values().count(b)>1:1/0    # no duplicate values
print map(''.join,zip(*[x for x in d.items()if x[0]!=x[1]])) # format, no no-ops

如果只是顺序没关系...


不应该a1,12返回a1,12来代替False?在“警告”部分下,据说翻译表为[a1,12]的“ a1”的值为12
fergusq

1
好了,您的TIO链接中的程序将返回False1a 21这也是错误的,因为必须保存啤酒。
fergusq

@fergusq固定。但是请注意,如果这是您要指的测试用例,则您的注释中有错别字,因为您说的a1,12不是a1,22
mbomb007 '17

我误会了你 您在问题编辑中提到了“警告”部分,但“警告”部分实际上处理的是另一种情况–不是双射规则。那让我感到困惑。
fergusq

它处理了一条不同的规则,但仍然说该测试用例的结果为假,这很重要。
mbomb007 '17

2

罗达108个 119字节

{c=[{_<>_|[[_,_]]|orderedUniq}()]d=[]e=[]c|_|{{d+=a;e+=b}if[a!=b]}for a,b[d,e]if[0,1]|{|n|c|[_[n]]|sort|count|[_2=1]}_}

在线尝试!

此函数从流中获取两个字符列表,然后将两个列表推入流中。

如果允许我返回配对,这可能是分类器。

说明(过时):

{
    c=[{
        _<>_|       /* pull two lists and interleave them */
        [[_,_]]|    /* "unflat", create lists from pairs */
        orderedUniq /* remove duplicates */
    }()]            /* c is a list of the pairs */
    d=[]
    e=[]
    c| /* push the pairs to the stream */
    _| /* flat */
    {  /* for each pair (a, b): */
        { /* if a != b (remove "1-to-1 relations"):  */
            d+=a;
            e+=b
        }if[a!=b]
    }for a,b
    /* return d and e if no character is mapped to more than one character */
    [d,e]if c|[_[0]]|sort|count|[_2=1]
}

这是一个不包含变量(114字节)的下划线解决方案:

{[[{_<>_}()|[[_,_]]|unorderedUniq]]|[[_()|_|[_]if[_1!=_2]],[_1()|_|[_2]if[_1!=_2]]]if[[_1()|_][::2],[_1()|_][1::2]]|[sort(_)|count|[_2=1]]}

有很多下划线。


怎么<>办?
Kritixi Lithos

@KritixiLithos这是交错运算符。a() <> b()interleave([a()], [b()])(或interleave(a, b),如果ab是数组)相同。
fergusq

这使a1 22 => false测试用例失败。“所有翻译都是彼此独立发生的,这是虚假的。”
mbomb007 '17

@ mbomb007我不太明白你说什么?您的意思是必须是双射,即。没有两个字符必须映射到同一字符吗?
fergusq

是。这就是问题所在。(每个字符只能在翻译的每一侧使用一次
mbomb007 '17

1

AWK,140个字节

BEGIN{RS="(.)"}RT~/\W/{S=1}RT~/\w/&&S{if(RT!=x=A[++b]){if(B[z=RT]==""){B[z]=x
c=c x
d=d z}a=B[z]!=x?0:a}}!S{A[++a]=RT}END{if(a==b)print c,d}

用法:FILE然后将代码放入:

awk -f FILE <<< "string1 string2"

输入字符串必须用空格分隔。

如果它们失败,则输出为空,或者2个字符串用空格分隔。


1

k,28个字节

{$[(y?y)~x?x;+?(~=/)#x,'y;]}

说明:

{                          } /function that takes in two strings, x and y
 $[         ;            ;]  /if statement (to check if there is a mapping)
         x?x                 /first index of [each letter in x] in x
   (y?y)                     /first index of [each letter in y] in y
        ~                    /make sure they match
                     x,'y    /zip together the two strings
               (~=/)#        /remove equal pairs
              ?              /unique pairs only
             +               /transpose ("unzip", in a way)

1

带有AGL的APL(Dyalog),22字节

{≡/⍳⍨¨⍺⍵:↓⍉↑∪⍺(≠é,¨)⍵}

在线尝试!

{}  匿名功能:

 如果…

  ⍺⍵ 论点

  ⍳⍨¨ 自索引时(即其元素在自身中的首次出现)

  ≡/ 等价的

: 然后:

  ⍺()⍵  对参数应用以下默认函数:

    连接相应的元素(长度不匹配的错误)

   é 然后用(é只是原始函数/)过滤

    字符串不同的地方

   唯一的(删除重复项)

  ↓⍉↑ 将配对列表转置为列表对(照明混合成表,转置表,分成列表)

 否则,什么都不做


1
耐心地等待这个答案的解释:P
魔术章鱼缸

1
@carusocomputing我在上面。
亚当

@carusocomputing好吗?
亚当

我错过了答复,对不起!↓⍉↑还是让我有些困惑。
魔术章鱼缸

1
@carusocomputing 也许有帮助吗?请注意,在APL和J中,矩阵与列表列表不同。
阿达姆(Adám)

0

CJam,38个字节

{_:,~={1\/;}:K~z{)\c=!},L|z_{_L|=K}%;}

输入和输出是堆栈上的数组。


0

PHP(> = 7.1),165个字节

for([,$x,$y]=$argv;a&$c=$x[$i];$t[$c]=$d)$z+=($d=$y[$i++])&&$d==($t[$c]??$d);foreach($t as$a=>$b)$a==$b?:$r[$a]=$b;print_r($z<$i|array_unique($r)<$t||a&$y[$i]?0:$t);

打印0其他虚假关联数组。在线运行-r或对其进行测试

分解

for([,$x,$y]=$argv;         # import arguments to $x and $y
    a&$c=$x[$i];            # loop through $x
    $t[$c]=$d)                  # 2. add pair to translation
$z+=                            # 1. increment $z if
    ($d=$y[$i++])&&             # there is a corresponding character in $y and
    $d==($t[$c]??$d);           # it equals a possible previous replacement
                            # remove identities from translation
foreach($t as$a=>$b)$a==$b?:$r[$a]=$b;
print_r(
    $z<$i                   # if not all tests passed
    |array_unique($t)<$t    # or there are duplicates in the translation
    ||a&$y[$i]              # or $y has more characters
    ?0                      # then print 0
    :$r                     # else print translation
);

是否允许关联数组作为输出?能否请您补充说,它的工作原理高于7.1版本
约尔格Hülsermann

@JörgHülsermann Output can be as an array or ...,所以我说是。我所有发布的内容都隐含了当前的PHP版本;但是,如果我发现重要的内容需要编辑,则将其添加。
泰特斯

有效情况仅显示数组输出的一种含义。如果还允许关联数组,我可以节省一些字节。如果允许,array_unique($r)!=$r并且在每种情况下,array_unique($r)<$r我都会为此技巧单独投票给您。在那一刻我在寻找一个解释
约尔格Hülsermann

@JörgHülsermann array_unique($t)<$t(必须更改,因为canto cnn无效)起作用,因为数组比较(不同于字符串比较)先比较长度。
泰特斯

测试cancnn花了我17个字节忘记我的建议
约尔格Hülsermann
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.