问题
I'm currently learning Python as I'm taking a data mining class. I was making a for-loop to make a noisy data file to do smoothing and I found a peculiarity on Python for-loop that I couldn't understand nor go around.
So I made this simple testing C++ and Python codes. C++ one works, but Python one doesn't.
The reason is that C++ allows arbitrary updates on the counter variable i within the for-loop block, but Python doesn't.
On Python code, I try to update i arbitrarily by doing i += 1 within the while-loop, but if you look at the outputs for At the first part of the loop, i = SOMETHING, Python is arbitrarily updating the i only in the while-loop that's in the for-loop, but then reverts the value back when it exits that while-loop.
(Outputs are in the comments at the bottom)
Why is that? Is it a scope issue? (Both C++ and Python are statically scoped) Is it because of their types? (I'm only familiar with statically-typed languages like C++ and Java, and not dynamically-typed languages like Python)
On Python, it seems like the for-loop is actually a function with return-by-value parameter i which ignores all the changes on the parameter that took place inside the function.
I tried:
- Setting the counter i as a global variable.
- using
range(0, len(input), *variable*), but I still failed to replicate it. - Researched if it can be solved by using Static variable or similar sort on Python (I think it's irrelevant?)
On Python, how would you replicate this C++ code? Could you enlighten me on why those for-loops behave differently? Thank you.
This is C++ code that's working correctly:
#include <stdio.h>
#include <string>
#include <iostream>
using namespace std;
int main()
{
string input = "abc defg";
string eachWord = "";
for(int i = 0; i < input.length(); i++)
{
cout << "At the first part of the loop, i = " << i << " ." << endl;
while(input[i] != ' ' && input[i] != '\0')
{
eachWord += input[i];
i++;
}
cout << eachWord << endl;
cout << "At the last part of the loop, i = " << i << " ." << endl << endl;
eachWord = "";
}
}
/*
Output:
At the first part of the loop, i = 0 .
abc
At the last part of the loop, i = 3 .
At the first part of the loop, i = 4 .
defg
At the last part of the loop, i = 8 .
*/
And this is the Python code that's not working correctly, that I tried to make to replicate the C++ code:
input = "abc defg"
eachWord = ''
for i in range(len(input)):
print("At the first part of the loop, i = ", i, ".")
while(input[i] != ' ' and input[i] != '\0'):
eachWord += input[i]
i += 1
print(eachWord)
print("At the last part of the loop, i = ", i, ".")
print()
eachWord = ''
"""
Output:
At the first part of the loop, i = 0 .
abc
At the last part of the loop, i = 3 .
At the first part of the loop, i = 1 .
bc
At the last part of the loop, i = 3 .
At the first part of the loop, i = 2 .
c
At the last part of the loop, i = 3 .
At the first part of the loop, i = 3 .
At the last part of the loop, i = 3 .
At the first part of the loop, i = 4 .
Traceback (most recent call last):
File "main.py", line 6, in <module>
while(input[i] != ' ' and input[i] != '\0'):
IndexError: string index out of range
"""
回答1:
First, replicating a c/c++ structure is not the best way to approach solving a problem. You will inevitably end up fighting against the language instead of benefiting from its strengths.
Secondly, to convert a c/c++ for loop, you have to realize that it is actually a while in disguise:
for (<initialization>,<condition>,<increment>)
{
// your stuff
}
Because Python for loops override the control variable (i) at each iteration, they can not translate directly to C/C++ loops that modify the control variable within their code block. These kinds of loops translate to this in Python (which is unwieldy and cumbersome):
<initialization>
while <condition>:
# your stuff
<increment>
for your particular example:
i = 0
while i < len(input):
# ...
i += 1
A more pythonic translation of you code would look more like this:
eachword = ''
for character in input:
if character in [' ','\0']: # will drop last word because no \0 at end of strings
print(eachword)
eachword = ''
else:
eachword += character
strings in python don't have a nul character at the end so the last word will likely be dropped unless your input comes from a non-standard source
Python has a built-in function to separate words in a string:
for eachword in input.split():
print(eachword)
回答2:
There are two main problems with the python I see;
Firstly the for loop does not work in the same way as the cpp for loop: python will reset i to go through the range, what you did with i inside the previous loops will be lost. Secondly python does not have a termination char on its strings like cpp does:
input = "abc defg"
eachWord = ''
i = 0
while(i < len(input)):
print("At the first part of the loop, i = ", i, ".")
while(i < len(input) and input[i] != ' '):
eachWord += input[i]
i += 1
print(eachWord)
print("At the last part of the loop, i = ", i, ".")
print()
eachWord = ''
i += 1
来源:https://stackoverflow.com/questions/61141152/c-for-loop-vs-python-for-loop