이온 컴파운드 골프 않아도되지만 다중 원자 이온 (예 :)에

도전

두 개의 입력, 즉 양이온과 음이온이 주어지면 두 이온으로 만들어진 이온 성 화합물에 대한 공식을 출력해야합니다. 이것은 기본적으로 요금이 0이되도록 균형을 맞추는 것을 의미합니다.

아래 첨자 번호로 수식 서식을 지정하지 않아도되지만 다중 원자 이온 (예 :)에 대괄호가 있어야합니다 NO3.

오류를 설명 할 필요는 없습니다 (예를 들어 누군가가 두 개의 음이온을 입력하는 경우 프로그램이 실패하게 할 수 있습니다).

참고 : Fe를 3+ 이상 충전하십시오

이온

설명해야 할 모든 이온은 AQA GCSE Chemistry Data Sheet 의 두 번째 부분에서 청구와 함께 발견됩니다. .

양이온

  • H +

  • Na +

  • Ag +

  • K +

  • +

  • NH 4 +

  • 2+

  • 캘리포니아 2+

  • Cu 2+

  • 마그네슘 2+

  • Zn 2+

  • Pb 2 이상

  • Fe 3+

  • 3+

음이온

  • CL

  • BR

  • F

  • OH

  • NO 3

  • O 2-

  • S 2-

  • SO 4 2-

  • CO 3 2-

몇 가지 예 :

HO 는 다음을 반환합니다.H2O

CaCO 3 반환 :-CaCO3

AlSO 4 는 다음을 반환합니다.Al2(SO4)3

다음 사항을 고려해야합니다.

HOH 반환 : – H2O 하지 H(OH)



답변

CJam, 176 바이트

"O S SO4 CO3 ""Cl Br F I OH NO3 """"H Na Ag K Li NH4 ""Ba Ca Cu Mg Zn Pb ""Fe Al "]_2{r\1$S+f#Wf=0#((z@}*_2$*_4=2*-_@/\@/@\]2/{~_({1$1>_el={'(@@')\}|0}&;}/]s"HOHH"1$#){;"H2O"}&

온라인으로 사용해보십시오

이것은 특히 괄호, 카운트, H2O 등을 나타내는 모든 특수 사례에서 다소 고통 스럽습니다.

데이터가 초소형 형식이 아닙니다. 더 잘릴 수는 있지만 해석하는 데 필요한 코드는 절약 효과를 보완 할 수 있습니다. 그래서 나는 각 배열에 -2에서 +3까지의 순서로 동일한 전하를 가진 원자를 포함하는 문자열 배열을 사용했습니다 (0의 문자열은 비어 있습니다).

설명:

[..]  Data, as explained above.
_     Duplicate data, will need it for both inputs.
2{    Loop over two inputs.
  r     Get input.
  \     Swap data to top.
  1$    Copy input to top (keep original for later).
  S+    Add a space to avoid ambiguity when searching in data.
  f#    Search for name in all strings of data.
  Wf=   Convert search results to truth values by comparing them to -1.
  0#    Find the 0 entry, which gives the index of the matching string.
  ((    Subtract 2, to get charge in range [-2, 3] from index.
  z     Absolute value, we don't really care about sign of charge.
  @     Swap second copy of data table to proper position for next input.
}*    End loop over two inputs.
_2$*  Multiply the two charges.
_4=   We need the LCM. But for the values here, only product 4 is not the LCM.
2*-   So change it to 2.
_@/   Divide LCM by first charge to get first count.
\@/   Divide LCM by second charge to get second count.
@\]2/ Make pairs of name/count for both ions...
{     ... and loop over the pairs.
  ~     Unpack the pair.
  _(    Check if count is > 1.
  {       Handle count > 1.
    1$    Get copy of name to top of stack.
    1>    Slice off first character to check if rest contains upper case.
    _el   Create lower case copy.
    =     If they are different, there are upper case letters.
    {       Handle case where parentheses are needed.
      '(    Opening parentheses.
      @@    Some stack shuffling to get values in place.
      ')    Closing parentheses.
      \     And one more swap to place count after parentheses.
    }|    End parentheses handling.
    0     Push dummy value to match stack layout of other branch.
  }&    End count handling.
  ;     Pop unused count off stack.
}/    End loop over name/count pairs.
]s    Pack stack content into single string, for H2O handling.
"HOHH"  String that contains both HOH and OHH, which need to be H2O.
1$#)  Check if output is in that string.
{     If yes, replace with H2O.
  ;     Drop old value.
  "H2O" And make it H2O instead.
}&    End of H2O handling.

답변

루아 , 174 242 바이트

나는 대괄호 ‘-_-를 잊어 버렸습니다. 그것은 242까지 올라갔습니다. 아, 적어도 재미있었습니다.

i,c,a={Ba=2,Ca=2,Cu=2,Mg=2,Zn=2,Pb=2,Fe=3,Al=3,O=2,S=2,SO4=2,CO3=2},io.read(),io.read()
p,d=i[c]~=i[a],{SO4=1,NO3=1,OH=1,CO3=1}
k,m=p and i[c]or'',p and i[a]or''
a=k==m and a or (d[a]and'('..a..')'or a)
print(c..a=='HOH'and'H2O'or c..m..a..k)

온라인으로 사용해보십시오!

구 버전:

i,c,a={Ba=2,Ca=2,Cu=2,Mg=2,Zn=2,Pb=2,Fe=3,Al=3,O=2,S=2,SO4=2,CO3=2},io.read(),io.read()
p=i[c]~=i[a]
k,m=p and i[c]or'',p and i[a]or''
print(c..a=='HOH'and'H2O'or c..m..a..k)

모든 값을 0으로 초기화하는 Lua의 경향을 악용하여 스토리지 비용을 줄일 수 있습니다. 여전히 루아는 여전히 약간 어색합니다 🙁


답변

자바 ( 619 647 667 바이트)

[Fixed] 업데이트 : H + OH는 하드 코딩하지 않아도 HOH를 반환합니다.

[Fixed] 업데이트 : 때때로 괄호가 나타나지 않아야 할 때 괄호가 나타남

암호

String f(String[]a){if(Arrays.equals(a,new String[]{"H","OH"})|Arrays.equals(a,new String[]{"OH","H"}))return "H2O";List<String>b=Arrays.asList(new String[]{"H","Na","Ag","K","Li","NH4","Ba","Ca","Cu","Mg","Zn","Pb","Fe","Al","Cl","Br","F","I","OH","NO3","O","S","SO4","CO3"});Integer[]c={1,1,1,1,1,1,2,2,2,2,2,2,3,3,1,1,1,1,1,1,2,2,2,2},d={5,18,19,22,23};List<Integer>j=Arrays.asList(d);int e=b.indexOf(a[0]),f=b.indexOf(a[1]),g=c[e],h=c[f],i;if(f<e){String p=a[0];a[0]=a[1];a[1]=p;i=g;g=h;h=i;i=e;e=f;f=i;}boolean k=j.contains(e),l=j.contains(f),m=g==h,n=g==1,o=h==1;return (k&!m&!o?"("+a[0]+")":a[0])+(m?"":h==1?"":h)+(l&!m&!n?"("+a[1]+")":a[1])+(m?"":g==1?"":g);}

나는 모든 이온 충전을 하드 코딩하지 않고이 작업을 수행하는 방법을 확신하지 못하여 결국 길었습니다. 운이 좋은 원인은 모든 전하가 1, 2 또는 3이므로 각 이온의 양을 쉽게 찾을 수 있습니다.

넓히는

import java.util.Arrays;
import java.util.List;
public class Compound {
    public static void main(String[]a){
        //System.out.println(f(a));
        String[] pos = new String[]{"H","Na","Ag","K","Li","NH4","Ba","Ca","Cu","Mg","Zn","Pb","Fe","Al"};
        String[] neg = new String[]{"Cl","Br","F","I","OH","NO3","O","S","SO4","CO3"};
        for(int i = 0; i < pos.length; i++){
            for(int j = 0; j < neg.length; j++){
                System.out.println(pos[i] + " + " + neg[j] + " = " + f(new String[]{pos[i],neg[j]}));
                System.out.println(neg[j] + " + " + pos[i] + " = " + f(new String[]{neg[j],pos[i]}));
            }
        }
    }
    static String f(String[]a){
        if(Arrays.equals(a,new String[]{"H","OH"})|Arrays.equals(a,new String[]{"OH","H"}))
            return "H2O";
        List<String>b=Arrays.asList(new String[]{"H","Na","Ag","K","Li","NH4","Ba","Ca","Cu","Mg","Zn","Pb","Fe","Al","Cl","Br","F","I","OH","NO3","O","S","SO4","CO3"});
        Integer[]c={1,1,1,1,1,1,2,2,2,2,2,2,3,3,1,1,1,1,1,1,2,2,2,2},d={5,18,19,22,23};
        List<Integer>j=Arrays.asList(d);
        int e=b.indexOf(a[0]),f=b.indexOf(a[1]),g=c[e],h=c[f],i;
        if(f<e){String p=a[0];a[0]=a[1];a[1]=p;i=g;g=h;h=i;i=e;e=f;f=i;}
        boolean k=j.contains(e),l=j.contains(f),m=g==h,n=g==1,o=h==1;
        return (k&!m&!o?"("+a[0]+")":a[0])+(m?"":o?"":h)+(l&!m&!n?"("+a[1]+")":a[1])+(m?"":n?"":g);
    }
}

여기 사용해보십시오

데이터

그들 중 하나라도 틀렸다면 알려주세요

H + Cl = HCl
Cl + H = HCl
H + Br = HBr
Br + H = HBr
H + F = HF
F + H = HF
H + I = HI
I + H = HI
H + OH = H2O
OH + H = H2O
H + NO3 = HNO3
NO3 + H = HNO3
H + O = H2O
O + H = H2O
H + S = H2S
S + H = H2S
H + SO4 = H2SO4
SO4 + H = H2SO4
H + CO3 = H2CO3
CO3 + H = H2CO3
Na + Cl = NaCl
Cl + Na = NaCl
Na + Br = NaBr
Br + Na = NaBr
Na + F = NaF
F + Na = NaF
Na + I = NaI
I + Na = NaI
Na + OH = NaOH
OH + Na = NaOH
Na + NO3 = NaNO3
NO3 + Na = NaNO3
Na + O = Na2O
O + Na = Na2O
Na + S = Na2S
S + Na = Na2S
Na + SO4 = Na2SO4
SO4 + Na = Na2SO4
Na + CO3 = Na2CO3
CO3 + Na = Na2CO3
Ag + Cl = AgCl
Cl + Ag = AgCl
Ag + Br = AgBr
Br + Ag = AgBr
Ag + F = AgF
F + Ag = AgF
Ag + I = AgI
I + Ag = AgI
Ag + OH = AgOH
OH + Ag = AgOH
Ag + NO3 = AgNO3
NO3 + Ag = AgNO3
Ag + O = Ag2O
O + Ag = Ag2O
Ag + S = Ag2S
S + Ag = Ag2S
Ag + SO4 = Ag2SO4
SO4 + Ag = Ag2SO4
Ag + CO3 = Ag2CO3
CO3 + Ag = Ag2CO3
K + Cl = KCl
Cl + K = KCl
K + Br = KBr
Br + K = KBr
K + F = KF
F + K = KF
K + I = KI
I + K = KI
K + OH = KOH
OH + K = KOH
K + NO3 = KNO3
NO3 + K = KNO3
K + O = K2O
O + K = K2O
K + S = K2S
S + K = K2S
K + SO4 = K2SO4
SO4 + K = K2SO4
K + CO3 = K2CO3
CO3 + K = K2CO3
Li + Cl = LiCl
Cl + Li = LiCl
Li + Br = LiBr
Br + Li = LiBr
Li + F = LiF
F + Li = LiF
Li + I = LiI
I + Li = LiI
Li + OH = LiOH
OH + Li = LiOH
Li + NO3 = LiNO3
NO3 + Li = LiNO3
Li + O = Li2O
O + Li = Li2O
Li + S = Li2S
S + Li = Li2S
Li + SO4 = Li2SO4
SO4 + Li = Li2SO4
Li + CO3 = Li2CO3
CO3 + Li = Li2CO3
NH4 + Cl = NH4Cl
Cl + NH4 = NH4Cl
NH4 + Br = NH4Br
Br + NH4 = NH4Br
NH4 + F = NH4F
F + NH4 = NH4F
NH4 + I = NH4I
I + NH4 = NH4I
NH4 + OH = NH4OH
OH + NH4 = NH4OH
NH4 + NO3 = NH4NO3
NO3 + NH4 = NH4NO3
NH4 + O = (NH4)2O
O + NH4 = (NH4)2O
NH4 + S = (NH4)2S
S + NH4 = (NH4)2S
NH4 + SO4 = (NH4)2SO4
SO4 + NH4 = (NH4)2SO4
NH4 + CO3 = (NH4)2CO3
CO3 + NH4 = (NH4)2CO3
Ba + Cl = BaCl2
Cl + Ba = BaCl2
Ba + Br = BaBr2
Br + Ba = BaBr2
Ba + F = BaF2
F + Ba = BaF2
Ba + I = BaI2
I + Ba = BaI2
Ba + OH = Ba(OH)2
OH + Ba = Ba(OH)2
Ba + NO3 = Ba(NO3)2
NO3 + Ba = Ba(NO3)2
Ba + O = BaO
O + Ba = BaO
Ba + S = BaS
S + Ba = BaS
Ba + SO4 = BaSO4
SO4 + Ba = BaSO4
Ba + CO3 = BaCO3
CO3 + Ba = BaCO3
Ca + Cl = CaCl2
Cl + Ca = CaCl2
Ca + Br = CaBr2
Br + Ca = CaBr2
Ca + F = CaF2
F + Ca = CaF2
Ca + I = CaI2
I + Ca = CaI2
Ca + OH = Ca(OH)2
OH + Ca = Ca(OH)2
Ca + NO3 = Ca(NO3)2
NO3 + Ca = Ca(NO3)2
Ca + O = CaO
O + Ca = CaO
Ca + S = CaS
S + Ca = CaS
Ca + SO4 = CaSO4
SO4 + Ca = CaSO4
Ca + CO3 = CaCO3
CO3 + Ca = CaCO3
Cu + Cl = CuCl2
Cl + Cu = CuCl2
Cu + Br = CuBr2
Br + Cu = CuBr2
Cu + F = CuF2
F + Cu = CuF2
Cu + I = CuI2
I + Cu = CuI2
Cu + OH = Cu(OH)2
OH + Cu = Cu(OH)2
Cu + NO3 = Cu(NO3)2
NO3 + Cu = Cu(NO3)2
Cu + O = CuO
O + Cu = CuO
Cu + S = CuS
S + Cu = CuS
Cu + SO4 = CuSO4
SO4 + Cu = CuSO4
Cu + CO3 = CuCO3
CO3 + Cu = CuCO3
Mg + Cl = MgCl2
Cl + Mg = MgCl2
Mg + Br = MgBr2
Br + Mg = MgBr2
Mg + F = MgF2
F + Mg = MgF2
Mg + I = MgI2
I + Mg = MgI2
Mg + OH = Mg(OH)2
OH + Mg = Mg(OH)2
Mg + NO3 = Mg(NO3)2
NO3 + Mg = Mg(NO3)2
Mg + O = MgO
O + Mg = MgO
Mg + S = MgS
S + Mg = MgS
Mg + SO4 = MgSO4
SO4 + Mg = MgSO4
Mg + CO3 = MgCO3
CO3 + Mg = MgCO3
Zn + Cl = ZnCl2
Cl + Zn = ZnCl2
Zn + Br = ZnBr2
Br + Zn = ZnBr2
Zn + F = ZnF2
F + Zn = ZnF2
Zn + I = ZnI2
I + Zn = ZnI2
Zn + OH = Zn(OH)2
OH + Zn = Zn(OH)2
Zn + NO3 = Zn(NO3)2
NO3 + Zn = Zn(NO3)2
Zn + O = ZnO
O + Zn = ZnO
Zn + S = ZnS
S + Zn = ZnS
Zn + SO4 = ZnSO4
SO4 + Zn = ZnSO4
Zn + CO3 = ZnCO3
CO3 + Zn = ZnCO3
Pb + Cl = PbCl2
Cl + Pb = PbCl2
Pb + Br = PbBr2
Br + Pb = PbBr2
Pb + F = PbF2
F + Pb = PbF2
Pb + I = PbI2
I + Pb = PbI2
Pb + OH = Pb(OH)2
OH + Pb = Pb(OH)2
Pb + NO3 = Pb(NO3)2
NO3 + Pb = Pb(NO3)2
Pb + O = PbO
O + Pb = PbO
Pb + S = PbS
S + Pb = PbS
Pb + SO4 = PbSO4
SO4 + Pb = PbSO4
Pb + CO3 = PbCO3
CO3 + Pb = PbCO3
Fe + Cl = FeCl3
Cl + Fe = FeCl3
Fe + Br = FeBr3
Br + Fe = FeBr3
Fe + F = FeF3
F + Fe = FeF3
Fe + I = FeI3
I + Fe = FeI3
Fe + OH = Fe(OH)3
OH + Fe = Fe(OH)3
Fe + NO3 = Fe(NO3)3
NO3 + Fe = Fe(NO3)3
Fe + O = Fe2O3
O + Fe = Fe2O3
Fe + S = Fe2S3
S + Fe = Fe2S3
Fe + SO4 = Fe2(SO4)3
SO4 + Fe = Fe2(SO4)3
Fe + CO3 = Fe2(CO3)3
CO3 + Fe = Fe2(CO3)3
Al + Cl = AlCl3
Cl + Al = AlCl3
Al + Br = AlBr3
Br + Al = AlBr3
Al + F = AlF3
F + Al = AlF3
Al + I = AlI3
I + Al = AlI3
Al + OH = Al(OH)3
OH + Al = Al(OH)3
Al + NO3 = Al(NO3)3
NO3 + Al = Al(NO3)3
Al + O = Al2O3
O + Al = Al2O3
Al + S = Al2S3
S + Al = Al2S3
Al + SO4 = Al2(SO4)3
SO4 + Al = Al2(SO4)3
Al + CO3 = Al2(CO3)3
CO3 + Al = Al2(CO3)3

노트

나는 Pyth에서 시작했지만 순서와 괄호에 짜증이 났습니다. 누군가가 그것을 끝내기를 원한다면 여기 에 있습니다.

=G["H" "Na" "Ag" "K" "Li" "NH4" "Ba" "Ca" "Cu" "Mg" "Zn" "Pb" "Fe" "Al" "Cl" "Br" "F" "I" "OH" "NO3" "O" "S" "SO4" "CO3" 1 1 1 1 1 1 2 2 2 2 2 2 3 3 1 1 1 1 1 1 2 2 2 2)J@G+24xG@QZK@G+24xG@Q1@QZ?kqJKK@Q1?kqJKJ

답변

자바 스크립트 (ES6), 316 277 바이트

더 쉬운 테스트를 위해 (CoffeeScript에서와 마찬가지로) pn변수를 세계화했습니다 . 변수를 지역화하면 문자 수에 차이가 없습니다.

f=(x,y)=>{i='indexOf',d='~NH4KNaAgLiBa~CaCuMgZnPbFeAlSO4CO3ClBrFIOHNO3',k=d[i](x),l=d[i](y),a=k<28?x:y,b=k<28?y:x,r=Math.ceil(k/11)-1,s=b=='F'?0:l<32;if(r==s)r=s=0;a=s&&a=='NH4'?'(NH4)':a;b=r&&/[A-Z]{2}/.test(b)?`(${b})`:b;return'H'==a&&b=='OH'?'H2O':a+(s?s+1:'')+b+(r?r+1:'')}


// Original attempt, 316 bytes
p={H:1,Na:1,Ag:1,K:1,Li:1,NH4:1,Ba:2,Ca:2,Cu:2,Mg:2,Zn:2,Pb:2,Fe:3,Al:3},n={Cl:1,Br:1,F:1,I:1,OH:1,NO3:1,O:2,S:2,SO4:2,CO3:2},f=(x,y)=>{a=p[x]?x:y,b=p[x]?y:x,z=p[a]==2&&n[b]==2,r=+z||n[b],s=+z||p[a];a=--r&&a=='NH4'?'(NH4)':a;b=--s&&/[A-Z]{2}/.test(b)?`(${b})`:b;return'H'==a&&b=='OH'?'H2O':a+(r?r+1:'')+b+(s?s+1:'')}

ES5 변형, 323 284 바이트

화살표 기능과 템플릿 문자열을 제거하는 것 외에 많은 변화가 없습니다.

f=function(x,y){i='indexOf',d='~NH4KNaAgLiBa~CaCuMgZnPbFeAlSO4CO3ClBrFIOHNO3',k=d[i](x),l=d[i](y),a=k<28?x:y,b=k<28?y:x,r=Math.ceil(k/11)-1,s=b=='F'?0:l<32;if(r==s)r=s=0;a=s&&a=='NH4'?'(NH4)':a;b=r&&/[A-Z]{2}/.test(b)?'('+b+')':b;return'H'==a&&b=='OH'?'H2O':a+(s?s+1:'')+b+(r?r+1:'')}


// Original attempt, 323 bytes
p={H:1,Na:1,Ag:1,K:1,Li:1,NH4:1,Ba:2,Ca:2,Cu:2,Mg:2,Zn:2,Pb:2,Fe:3,Al:3},n={Cl:1,Br:1,F:1,I:1,OH:1,NO3:1,O:2,S:2,SO4:2,CO3:2},f=function(x,y){a=p[x]?x:y,b=p[x]?y:x,z=p[a]==2&&n[b]==2,r=+z||n[b],s=+z||p[a];a=--r&&a=='NH4'?'(NH4)':a;b=--s&&/[A-Z]{2}/.test(b)?'('+b+')':b;return'H'==a&&b=='OH'?'H2O':a+(r?r+1:'')+b+(s?s+1:'')}
f=function(x,y){i='indexOf',d='~NH4KNaAgLiBa~CaCuMgZnPbFeAlSO4CO3ClBrFIOHNO3',k=d[i](x),l=d[i](y),a=k<28?x:y,b=k<28?y:x,r=Math.ceil(k/11)-1,s=b=='F'?0:l<32;if(r==s)r=s=0;a=s&&a=='NH4'?'(NH4)':a;b=r&&/[A-Z]{2}/.test(b)?'('+b+')':b;return'H'==a&&b =='OH'?'H2O':a+(s?s+1:'')+b+(r?r+1:'')}

;['H', 'Na', 'Ag', 'K', 'Li', 'NH4', 'Ba', 'Ca', 'Cu', 'Mg', 'Zn', 'Pb', 'Fe', 'Al'].forEach(function (q) {
    ['Cl', 'Br', 'F', 'I', 'OH', 'NO3', 'O', 'S', 'SO4', 'CO3'].forEach(function (w) {
        document.body.innerHTML += '<p>' + q + ' + ' + w + ' = ' + f(q, w);
    });
});

답변

CoffeeScript, 371 333 바이트

이 수에는 줄 바꿈이 포함됩니다 (일부 개행은 세미콜론으로 대체 될 수 있지만 문자 수에는 영향을 미치지 않습니다)

f=(x,y)->(i='indexOf';d='~NH4KNaAgLiBa~CaCuMgZnPbFeAlSO4CO3ClBrFIOHNO3';k=d[i] x;r=-1+Math.ceil k/11;l=d[i] y;a=if k<28then x else y
b=if k<28then y else x
s=if b=='F'then 0else 32>l
r=s=0if r==s;a='(NH4)'if'NH4'==a&&s;b='('+b+')'if/[A-Z]{2}/.test(b)&&r;if'H'==a&&b=='OH'then'H2O'else a+(if!s then''else 1+s)+b+(if!r then''else 1+r))

# Original attempt, 371 bytes
p={H:1,Na:1,Ag:1,K:1,Li:1,NH4:1,Ba:2,Ca:2,Cu:2,Mg:2,Zn:2,Pb:2,Fe:3,Al:3}
n={Cl:1,Br:1,F:1,I:1,OH:1,NO3:1,O:2,S:2,SO4:2,CO3:2}
f=(x,y)->(a=if p[x]then x else y
b=if p[x]then y else x
z=p[a]==n[b]==2;r=+z||n[b];s=+z||p[a];if--r&&a=='NH4'then a='(NH4)'
if--s&&/[A-Z]{2}/.test(b)then b='('+b+')'
if'H'==a&&b=='OH'then'H2O'else a+(if!r then''else r+1)+b+(if!s then''else s+1))

답변

CJam (137 바이트)

{{"SO4CO3ClBrFINO3OHNaAgKLiNH4BaCaCuMgZnPbFeAl":I\#~}$_s"HOH"="HO"1/@?_{I\#G-_0<B*-B/_W>+z}%_~1$=\1?f/W%[.{:T1>{_{'a<},,1>{'(\')}*T}*}]s}

이것은 익명의 블록 (함수)으로 두 개의 이온을 목록에 싸인 문자열로 가져 와서 문자열을 반환합니다.

온라인 데모 .

해부

{                        e# Begin a block
  {                      e#   Sort the input list
    "SO4...Al"           e#     Ions in ascending order of charge
    :I                   e#     Stored as I for future reuse
    \#~                  e#     Index and bit-invert to sort descending
  }$

  _s"HOH"="HO"1/@?       e#   Special case for water: replace ["H" "OH"] with ["H" "O"]

  _{I\#G-_0<B*-B/_W>+z}% e#   Copy the list and hash index in I to find the charges
  _~1$=\1?f/             e#   Replace [2 2] by [1 1]
  W%                     e#   Reverse the charges
  [                      e#   Gather in an array
    .{                   e#   Pairwise for each ion and its opponent's reduced charge...
      :T1>{              e#     If the charge (copied to T) is greater than 1
        _{'a<},,         e#       Count the characters in the ion which are before 'a'
        1>{'(\')}*       e#       If there's more than one, add some parentheses
        T                e#       Append T
      }*
    }
  ]
  s                      e#   Flatten the list to a single string
}

답변

파이썬 3 , 364 바이트

index+12 차원 배열에서 와 같이 전하의 절대 값으로 이온을 저장합니다 (0 인덱스 요소에는 + -1 전하 등이 있음). string.split ()을 사용하여 몇 개의 문자를 저장합니다. H + OH = H2O먼저 특수한 경우를 처리 한 다음 두 전하의 LCM을 전하로 나눈 각 종류에 필요한 이온 수를 계산합니다. 그런 다음 필요한 경우 실제 이온 수뿐만 아니라 괄호로 묶습니다.

from math import*
o=["NH4 NO3 H Na Ag K Li OH I F Br Cl".split(),"CO3 SO4 Ba Ca Cu Mg Zn Pb S O".split(),["Fe","Al"]]
p=["H","OH"]
def c(i):
 for h,k in enumerate(o):
  if i in k:return-~h
def b(x,y):
 if x in p and y in p:return"H20"
 i,j=c(x),c(y);g=gcd(i,j);i//=g;j//=g;return((x,"(%s)"%x)[x[-1]in"34"]+str(j),x)[j==1]+((y,"(%s)"%y)[y[-1]in"34"]+str(i),y)[i==1]

온라인으로 사용해보십시오!