0
$\begingroup$

I got England and German soccer data with the following:

dataENG = 
  Import["https://www.soccerstats.com/results.asp?league=england&\
pmtype=bydate", "Data"];
Drop[Drop[Drop[Cases[dataENG, {_, _, _, _}, Infinity], -4], -1, None],
   None, {1, 4, 3}];
Table[If[StringContainsQ[%[[i, 1]], "-"] == True && 
    StringContainsQ[%[[i, 2]], "-"] == True , %[[i]], ## &[]], {i, 1, 
   Length[%]}];
Table[StringSplit[%[[i]], "-"], {i, 1, Length[%]}];
resultsENG = 
  Transpose[{StringTrim[%[[All, 1, 1]]], 
    ToExpression[StringTrim[%[[All, 2, 1]]]], 
    StringTrim[%[[All, 1, 2]]], 
    ToExpression[StringTrim[%[[All, 2, 2]]]]}];
teamsENG = StringTrim[Union[Transpose[resultsENG][[1]]]];
nENG = Length[resultsENG];
mENG = Length[teamsENG];

dataGER = 
  Import["https://www.soccerstats.com/results.asp?league=germany&\
pmtype=bydate", "Data"];
Drop[Drop[Drop[Cases[dataGER, {_, _, _, _}, Infinity], -4], -1, None],
   None, {1, 4, 3}];
Table[If[StringContainsQ[%[[i, 1]], "-"] == True && 
    StringContainsQ[%[[i, 2]], "-"] == True , %[[i]], ## &[]], {i, 1, 
   Length[%]}];
Table[StringSplit[%[[i]], "-"], {i, 1, Length[%]}];
resultsGER = 
  Transpose[{StringTrim[%[[All, 1, 1]]], 
    ToExpression[StringTrim[%[[All, 2, 1]]]], 
    StringTrim[%[[All, 1, 2]]], 
    ToExpression[StringTrim[%[[All, 2, 2]]]]}];
teamsGER = StringTrim[Union[Transpose[resultsGER][[1]]]];
nGER = Length[resultsGER];
mGER = Length[teamsGER];

Now, I want to get the vector goalsfor for England and German Leagues; here the code I wrote:

    results1 = {resultsENG, resultsGER};    
    n1 = {nENG, nGER};
    t1 = {teamsENG, teamsGER};
    m1 = {mENG, mGER};
    goalsfor = ConstantArray[0, Dimensions[Flatten[t1]]];
    For[k = 1, k = Length[n1], k++,
      Do[Table[
        If[results1[[i, All, 1]] == t1[[i, j]], 
         goalsfor[[j]] = 
          goalsfor[[j]] + results1[[i, All, 2]], ## &[]], {i, 1, 
         n1[[k]]} ], {j, 1, m1[[k]]}]];

It sounds good, I should have a vector of numbers equal to the goals of the teams, but if I call goalsfor I get as a result a constant array of zeros. Where I am wrong?

$\endgroup$
  • $\begingroup$ Welcome to Mathematica SE! I wonder if you can rewrite this without a For loop? It should not be difficult to do so using just Table, and may function better/help you to learn more! $\endgroup$ – CA Trevillian Jan 2 at 16:38
3
$\begingroup$

After some restructuring, and if all you're interested in is the number of goals for each team

dateQ = Composition[Quiet, NumberQ, AbsoluteTime]; (*https://mathematica.stackexchange.com/a/49112/46490*)

countries = {"ENG", "GER"};
Evaluate[countrydata /@ countries] = With[
  {data = Import["https://www.soccerstats.com/results.asp?league=" <> # <> "&pmtype=bydate", "Data"]}, 
  Cases[
    data,
    {_?dateQ, teams_?(Not@*StringContainsQ[DigitCharacter]), score_, _} :> MapAt[ToExpression, StringTrim@StringSplit[#, " - "] & /@ {teams, score}, 2],
    ∞
  ]
] & /@ {"england", "germany"};

goalsfor = Join @@ Table[
  (#1[[2]] -> #2) & @@@ Total[#, {2}] &@GatherBy[Join @@ (Transpose /@ countrydata[country]), First],
  {country, countries}
] // Association

<|"Arsenal" -> 26, "Chelsea" -> 35, "Liverpool" -> 47, "Wolverhampton" -> 29, "Manchester City" -> 54, "Sheffield Utd" -> 23, "Brighton" -> 24, "Bournemouth" -> 20, "Newcastle Utd" -> 20, "Everton" -> 23, "Southampton" -> 24, "Crystal Palace" -> 18, "Watford" -> 15, "Aston Villa" -> 25, "Norwich City" -> 21, "Tottenham" -> 36, "West Ham Utd" -> 21, "Leicester City" -> 43, "Burnley" -> 23, "Manchester Utd" -> 32, "Dusseldorf" -> 15, "Union Berlin" -> 19, "Paderborn" -> 19, "E. Frankfurt" -> 27, "Bayern Munich" -> 43, "Wolfsburg" -> 17, "FC Koln" -> 18, "Werder Bremen" -> 22, "FSV Mainz" -> 24, "Leverkusen" -> 21, "RB Leipzig" -> 47, "FC Augsburg" -> 26, "Hertha Berlin" -> 22, "Monchengladbach" -> 33, "Hoffenheim" -> 23, "Dortmund" -> 41, "Freiburg" -> 25|>

The important parts being the implementation of Cases. The pattern

{_?dateQ, teams_?(Not@*StringContainsQ[DigitCharacter]), score_, _}

only picks out the four element lists with dates as the first element and the second element that doesn't contain any number characters (Not@*StringContainsQ[DigitCharacter] could be replaced with StringFreeQ[#, DigitCharacter] & but I like the operator form of the prior). Then the rhs of the rule

(StringTrim@StringSplit[#, " - "] & /@ {teams, score})

automatically picks out and changes the teams and scores to the right format.

$\endgroup$
  • $\begingroup$ Amazing Gravity Guy, thank you! Actually I'm not interested only in number of goals for each team, this is just part of my project. I would like to do an outcomes prediction program based on already played matches in the season which takes into account: - teams "home/away goals"; - "home factor advantage" - "healt status" based on the last five results of teams. I'd like to introduce also other predictive factors (nr. shoots for field areas, nr. succeeded passages), but as you can see I'm approaching to programming very recently. For now I'm trying to focus just on first point. $\endgroup$ – Mick Jan 1 at 13:45
  • $\begingroup$ I posted a similar issue here: mathematica.stackexchange.com/questions/214507/… $\endgroup$ – Mick Feb 11 at 14:57
1
$\begingroup$

I modified the code as follows:

   Do[Do[Do[Table[
     If[results[[i, l, 1]] == teams[[i, j]], 
      goalsfor[[i, j]] = 
       goalsfor[[i, j]] + results[[i, l, 2]], ## &[]], {l, 1, 
      n[[k]]}] && 
    Table[
     If[results[[i, l, 3]] == teams[[i, j]], 
      goalsfor[[i, j]] = 
       goalsfor[[i, j]] + results[[i, l, 4]], ## &[]], {l, 1, 
      n[[k]]}], {j, 1, m[[k]]}], {i, {k}}], {k, 1, Length[n]}]

It seems really working now.

$\endgroup$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.